简体   繁体   中英

Parsing lines of text from external file in Ruby

I am trying to parse a raw email. The desired result is a hash of the lines that contain specific headers.

This is the Ruby file:

raw_email = File.open("sample-email.txt", "r")
parsed_email = Hash.new('')

raw_email.each do |line|
  puts line
  header = line.chomp(":")
  puts header
  if header == "Delivered-To"
    parsed_email[:to] = line
  elsif header == "From"
    parsed_email[:from] = line
  elsif header == "Date"
    parsed_email[:date] = line
  elsif header == "Subject"
    parsed_email[:subject] = line
  end
end

puts parsed_email

And this is the raw email:

Delivered-To: user1@example.com
From: John Doe <user2@example.com>
Date: Tue, 12 Dec 2017 13:30:14 -0500
Subject: Testing the parser
To: user1@example.com
Content-Type: multipart/alternative; 
boundary="123456789abcdefghijklmnopqrs"

--123456789abcdefghijklmnopqrs
Content-Type: text/plain; charset="UTF-8"

Lorem ipsum dolor sit amet, consectetur adipiscing elit. Integer nec 
odio. Praesent libero. Sed cursus ante dapibus diam. Sed nisi. Nulla 
quis sem at nibh elementum imperdiet. Duis sagittis ipsum.

--123456789abcdefghijklmnopqrs
Content-Type: text/html; charset="UTF-8"

<div dir="ltr">Lorem ipsum dolor sit amet, consectetur adipiscing 
elit. Integer nec odio. Praesent libero. Sed cursus ante dapibus diam. 
Sed nisi. Nulla quis sem at nibh elementum imperdiet. Duis sagittis 
ipsum.<br clear="all">
</div>

--089e082c24dc944a9f056028d791--

The puts statements are just for my own testing to see if data is being passed along.

What I am getting is each full line put twice and an empty hash put at the end.

I have also tried changing different bits to strings or arrays and I've also tried using line.split(":", 1) instead of line.chomp(":")

Can someone please explain why this isn't working?

Try this

raw_email = File.open("sample-email.txt", "r")
parsed_email = {}

raw_email.each do |line|
  case line.split(":")[0]
  when "Delivered-To"
    parsed_email[:to] = line
  when "From"
    parsed_email[:from] = line
  when "Date"
    parsed_email[:date] = line
  when "Subject"
    parsed_email[:subject] = line
  end
end

puts parsed_email
=> {:to=>"Delivered-To: user1@example.com\n", :from=>"From: John Doe <user2@example.com>\n", :date=>"Date: Tue, 12 Dec 2017 13:30:14 -0500\n", :subject=>"Subject: Testing the parser\n"}

Explanation You need to split line on : and select first. Like this line.split(":")[0]

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM