Как добавить значение между некоторыми значениями в консоли рельсов - PullRequest
0 голосов
/ 24 октября 2018

В моей базе данных есть следующие записи

[662] #<ChapterSolution:0x000055ec31cdfb40> {
            :id => 5071,
    :chapter_id => 221,
    :created_at => Tue, 19 Sep 2017 18:24:57 IST +05:30,
    :updated_at => Sat, 02 Dec 2017 10:24:53 IST +05:30,
      :question => "11",
          :part => "i",
        :answer => "See Explanation",
      :solution => "<img src='//cdn.google.in/editor/pictures/573/content.jpeg' />"

[663] #<ChapterSolution:0x000055ec31cdfb40> {
            :id => 5071,
    :chapter_id => 221,
    :created_at => Tue, 19 Sep 2017 18:24:57 IST +05:30,
    :updated_at => Sat, 02 Dec 2017 10:24:53 IST +05:30,
      :question => "11",
          :part => "i",
        :answer => "See Explanation",
      :solution => "<img src='//cdn.google.in/editor/pictures/574/content.jpeg' />"

[664] #<ChapterSolution:0x000055ec31cdfb40> {
            :id => 5071,
    :chapter_id => 221,
    :created_at => Tue, 19 Sep 2017 18:24:57 IST +05:30,
    :updated_at => Sat, 02 Dec 2017 10:24:53 IST +05:30,
      :question => "11",
          :part => "i",
        :answer => "See Explanation",
      :solution => "<img src='//cdn.google.in/editor/pictures/575/content.jpeg' />"

Я хочу добавить https: в значение решения в каждой записи, между img src = 'и // cdn.google ... , чтобы сделать правильный URL в каждой записи,

однако я не могу понять, как это сделать, любая помощь / предложения будут оценены.

Ответы [ 5 ]

0 голосов
/ 25 октября 2018

Я не знаю, является ли это лучшим способом сделать это, но эй, это сработало для меня.

object = ChapterSolution.where("solution ~* 'src=[\\''|\"]//'")
object.each do |cs|
    cs.solution = cs.solution.split("src='").join("src='https:")
    cs.save
end
0 голосов
/ 24 октября 2018

Альтернативное решение более высокого уровня, которое избегает использования регулярных выражений, заключается в использовании HTML-парсера ( Nokogiri ) и модуля URI :

# using .find_each loads the records in batches
ChapterSolution.find_each do |cs|
  frag = Nokogiri::HTML.fragment(cs.solution)
  uri = URI.parse(frag.children.first["src"])
  uri.scheme = 'https'

  # Use this if you want to keep the HTML tag
  frag.children.first["src"] = uri.to_s
  cs.update_column(:solution, frag.to_s)

  # or this if you want to strip the HTML and only keep the URI 
  cs.update_column(:solution, uri.to_s)
end

Плюсыздесь обновление в БД с помощью регулярного выражения заключается в том, что он сможет обрабатывать гораздо большие вариации входного HTML и может гарантировать, что выходные данные содержат действительный URI.

Дело в том, что он будет намного медленнее.

0 голосов
/ 24 октября 2018

Если вы хотите обновить solution данные столбца, и они имеют такую ​​же форму, как '<img src='//cdn......'

update [table name]
   set solution = substring(solution, 1, 10)||'https:'||substring(solution, 11);
0 голосов
/ 24 октября 2018

Извлечение всех записей и последующее использование регулярного выражения в Ruby для индивидуального обновления записей не очень эффективно.

На самом деле вы можете использовать функции сопоставления с образцом в Postgres для выполненияодин запрос UPDATE, который обновляет все записи одновременно:

ChapterSolution.where("solution ~* 'src=[\\''|\"]//'").update_all(
  "solution = regexp_replace(chapter_solutions.solution, '//(.*)[\\''|\"]', 'https://\\1')"
)

Это приводит к:

irb(main):014:0> ChapterSolution.all.map(&:solution)
  ChapterSolution Load (0.8ms)  SELECT "chapter_solutions".* FROM "chapter_solutions"
=> ["<img src='https://cdn.google.in/editor/pictures/573/content.jpeg />", "<img src='https://cdn.google.in/editor/pictures/574/content.jpeg />", "<img src='https://cdn.google.in/editor/pictures/575/content.jpeg />"]

Если вы также хотите удалить HTML, измените регулярное выражение:

ChapterSolution.where("solution ~* 'src=[\\''|\"]//'").update_all(
  "solution = regexp_replace(chapter_solutions.solution, '.*\\ssrc=[\''|\"]\/\/(.*)[\\''|\"].*', 'https://\\1')"
)
0 голосов
/ 24 октября 2018

дешевый способ - использовать gsub и регулярные выражения:

object[:solution].gsub(/img src='\/\//,"img src='https://")

документация gsub

...