ish_models 3.0.0.1 → 3.1.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/MIT-LICENSE +20 -0
- data/README.md +28 -0
- data/Rakefile +15 -0
- data/app/assets/config/ish_models_manifest.js +1 -0
- data/app/assets/stylesheets/ish_models/application.css +15 -0
- data/app/controllers/ish_models/application_controller.rb +4 -0
- data/app/helpers/ish_models/application_helper.rb +4 -0
- data/app/jobs/ish_models/application_job.rb +4 -0
- data/app/mailers/ish_models/application_mailer.rb +6 -0
- data/app/models/ish_models/application_record.rb +5 -0
- data/app/views/layouts/ish_models/application.html.erb +15 -0
- data/config/routes.rb +2 -0
- data/lib/ish_models/engine.rb +5 -0
- data/lib/ish_models/version.rb +3 -0
- data/lib/ish_models.rb +5 -93
- data/lib/tasks/ish_models_tasks.rake +4 -0
- data/lib/{office/admin_message.rb → wco/profile.rb} +2 -5
- metadata +42 -165
- data/lib/address.rb +0 -20
- data/lib/feature.rb +0 -32
- data/lib/gallery.rb +0 -66
- data/lib/gameui/asset3d.rb +0 -33
- data/lib/gameui/map.rb +0 -260
- data/lib/gameui/map_bookmark.rb +0 -9
- data/lib/gameui/marker.rb +0 -128
- data/lib/iro/option_watch.rb +0 -72
- data/lib/ish/cache_key.rb +0 -14
- data/lib/ish/configuration.rb +0 -11
- data/lib/ish/crawler.rb +0 -26
- data/lib/ish/email_campaign.rb +0 -55
- data/lib/ish/email_context.rb +0 -113
- data/lib/ish/email_template.rb +0 -115
- data/lib/ish/email_unsubscribe.rb +0 -19
- data/lib/ish/event.rb +0 -20
- data/lib/ish/image_asset.rb +0 -38
- data/lib/ish/invoice.rb +0 -130
- data/lib/ish/lorem_ipsum.rb +0 -30
- data/lib/ish/meeting.rb +0 -31
- data/lib/ish/payment.rb +0 -29
- data/lib/ish/premium_item.rb +0 -13
- data/lib/ish/railtie.rb +0 -8
- data/lib/ish/user_profile.rb +0 -149
- data/lib/ish/utils.rb +0 -45
- data/lib/mongoid/votable.rb +0 -247
- data/lib/mongoid/voter.rb +0 -96
- data/lib/newsitem.rb +0 -94
- data/lib/office/action.rb +0 -32
- data/lib/office/action_tie.rb +0 -16
- data/lib/office/directmail_envelope.rb +0 -51
- data/lib/office/email_action.rb +0 -34
- data/lib/office/email_action_tie.rb +0 -18
- data/lib/office/email_attachment.rb +0 -12
- data/lib/office/email_conversation.rb +0 -102
- data/lib/office/email_conversation_lead.rb +0 -11
- data/lib/office/email_conversation_tag.rb +0 -14
- data/lib/office/email_filter.rb +0 -45
- data/lib/office/email_message.rb +0 -192
- data/lib/office/email_message_stub.rb +0 -22
- data/lib/office/emailtag.rb +0 -27
- data/lib/office/emailtag_email_conversation.rb +0 -10
- data/lib/office/lead_action.rb +0 -24
- data/lib/office/lead_action_template.rb +0 -47
- data/lib/office/obfuscated_redirect.rb +0 -12
- data/lib/office/scheduled_email_action.rb +0 -62
- data/lib/photo.rb +0 -87
- data/lib/report.rb +0 -65
- data/lib/video.rb +0 -91
- data/lib/wco/appliance.rb +0 -52
- data/lib/wco/appliance_tmpl.rb +0 -56
- data/lib/wco/dns_domain.rb +0 -23
- data/lib/wco/email_conversation_lead.rb +0 -10
- data/lib/wco/leadset.rb +0 -26
- data/lib/wco/price.rb +0 -30
- data/lib/wco/product.rb +0 -35
- data/lib/wco/serverhost.rb +0 -140
- data/lib/wco/subscription.rb +0 -25
@@ -1,51 +0,0 @@
|
|
1
|
-
require 'prawn'
|
2
|
-
|
3
|
-
class Office::DirectmailEnvelope
|
4
|
-
include Mongoid::Document
|
5
|
-
include Mongoid::Timestamps
|
6
|
-
|
7
|
-
|
8
|
-
## 72 points per inch
|
9
|
-
## 72 ppi
|
10
|
-
def self.list_to_envelopes props
|
11
|
-
from = props[:from]
|
12
|
-
|
13
|
-
pdf = Prawn::Document.new({ page_size: [ 9.5*72, 4.12*72 ], :margin => [0,0,0,0] })
|
14
|
-
|
15
|
-
pdf.canvas do
|
16
|
-
|
17
|
-
props[:tos].each_with_index do |to, idx|
|
18
|
-
print '.'
|
19
|
-
|
20
|
-
pdf.bounding_box( [ 0.5*72, 3.5*72 ], width: 3*72, height: 2*72 ) do
|
21
|
-
# pdf.transparent(0.5) { pdf.stroke_bounds }
|
22
|
-
|
23
|
-
pdf.text from[:name]
|
24
|
-
pdf.text from[:address_1]
|
25
|
-
pdf.text from[:address_2]
|
26
|
-
pdf.text from[:address_3]
|
27
|
-
end
|
28
|
-
|
29
|
-
pdf.bounding_box( [ 4*72, 2.5*72 ], width: 4*72, height: 2*72 ) do
|
30
|
-
# pdf.transparent(0.5) { pdf.stroke_bounds }
|
31
|
-
|
32
|
-
pdf.text to[:name]
|
33
|
-
pdf.text to[:address_1]
|
34
|
-
pdf.text to[:address_2]
|
35
|
-
pdf.text to[:address_3]
|
36
|
-
end
|
37
|
-
|
38
|
-
if idx+1 != props[:tos].length
|
39
|
-
pdf.start_new_page
|
40
|
-
end
|
41
|
-
|
42
|
-
end
|
43
|
-
|
44
|
-
end
|
45
|
-
|
46
|
-
return pdf
|
47
|
-
end
|
48
|
-
|
49
|
-
end
|
50
|
-
ODE = ::Office::DirectmailEnvelope
|
51
|
-
|
data/lib/office/email_action.rb
DELETED
@@ -1,34 +0,0 @@
|
|
1
|
-
|
2
|
-
##
|
3
|
-
## 2023-03-04 _vp_ When I receive one.
|
4
|
-
## 2023-03-04 _vp_ When I send one, forever.
|
5
|
-
##
|
6
|
-
class Office::EmailAction
|
7
|
-
include Mongoid::Document
|
8
|
-
include Mongoid::Timestamps
|
9
|
-
|
10
|
-
field :slug, type: :string
|
11
|
-
validates :slug, uniqueness: true, allow_nil: true
|
12
|
-
|
13
|
-
field :descr, type: :string ## optional, can remove
|
14
|
-
|
15
|
-
belongs_to :email_template, class_name: '::Ish::EmailTemplate'
|
16
|
-
def tmpl; email_template; end
|
17
|
-
|
18
|
-
has_many :scheduled_email_actions, class_name: '::Office::ScheduledEmailAction'
|
19
|
-
def schs; scheduled_email_actions; end
|
20
|
-
|
21
|
-
has_many :ties, class_name: '::Office::EmailActionTie', inverse_of: :email_action
|
22
|
-
has_many :prev_ties, class_name: '::Office::EmailActionTie', inverse_of: :next_email_action
|
23
|
-
accepts_nested_attributes_for :ties
|
24
|
-
|
25
|
-
has_many :email_filters, class_name: 'Office::EmailFilter', inverse_of: :email_action
|
26
|
-
|
27
|
-
field :deleted_at, default: nil, type: :time
|
28
|
-
|
29
|
-
def self.list
|
30
|
-
[[nil,nil]] + Office::EmailAction.where({ :deleted_at => nil }).map { |a| [ a.slug, a.id ] }
|
31
|
-
end
|
32
|
-
|
33
|
-
end
|
34
|
-
EAct = Office::EmailAction
|
@@ -1,18 +0,0 @@
|
|
1
|
-
|
2
|
-
##
|
3
|
-
## act = Act.new ; tie = Actie.new; act.ties.push( tie )
|
4
|
-
##
|
5
|
-
class Office::EmailActionTie
|
6
|
-
include Mongoid::Document
|
7
|
-
include Mongoid::Timestamps
|
8
|
-
|
9
|
-
attr_accessor :to_delete
|
10
|
-
|
11
|
-
belongs_to :email_action, class_name: '::Office::EmailAction', inverse_of: :ties
|
12
|
-
belongs_to :next_email_action, class_name: '::Office::EmailAction', inverse_of: :prev_ties
|
13
|
-
|
14
|
-
field :next_at_exe, type: :string
|
15
|
-
validates :next_at_exe, presence: true
|
16
|
-
|
17
|
-
end
|
18
|
-
EActie = Office::EmailActionTie
|
@@ -1,12 +0,0 @@
|
|
1
|
-
|
2
|
-
class Office::EmailAttachment
|
3
|
-
include Mongoid::Document
|
4
|
-
include Mongoid::Timestamps
|
5
|
-
|
6
|
-
belongs_to :email_message, class_name: 'Office::EmailMessage', inverse_of: :email_attachments
|
7
|
-
|
8
|
-
field :content
|
9
|
-
field :content_type
|
10
|
-
field :filename
|
11
|
-
|
12
|
-
end
|
@@ -1,102 +0,0 @@
|
|
1
|
-
|
2
|
-
class Office::EmailConversation
|
3
|
-
include Mongoid::Document
|
4
|
-
include Mongoid::Timestamps
|
5
|
-
include Mongoid::Paranoia
|
6
|
-
|
7
|
-
STATE_UNREAD = 'state_unread'
|
8
|
-
STATE_READ = 'state_read'
|
9
|
-
STATES = [ STATE_UNREAD, STATE_READ ]
|
10
|
-
field :state
|
11
|
-
|
12
|
-
field :subject
|
13
|
-
index({ subject: -1 })
|
14
|
-
|
15
|
-
field :latest_at
|
16
|
-
index({ latest_at: -1 })
|
17
|
-
|
18
|
-
field :from_emails, type: :array, default: []
|
19
|
-
index({ from_emails: -1 })
|
20
|
-
|
21
|
-
field :preview, default: ''
|
22
|
-
|
23
|
-
# @deprecated, @TODO: remove
|
24
|
-
has_many :lead_ties, class_name: 'Office::EmailConversationLead'
|
25
|
-
has_many :wco_lead_ties, class_name: '::Wco::EmailConversationLead'
|
26
|
-
|
27
|
-
|
28
|
-
def leads
|
29
|
-
Lead.find( lead_ties.map( &:lead_id ) )
|
30
|
-
end
|
31
|
-
|
32
|
-
has_many :email_messages, class_name: 'Office::EmailMessage'
|
33
|
-
has_many :email_conversation_tags, class_name: 'Office::EmailConversationTag'
|
34
|
-
has_many :emailtag_ties, class_name: 'Office::EmailtagEmailConversation'
|
35
|
-
|
36
|
-
def tags
|
37
|
-
Emailtag.find( emailtag_ties.map &:emailtag_id )
|
38
|
-
end
|
39
|
-
|
40
|
-
# ## Tested manually ok, does not pass the spec. @TODO: hire to make pass spec? _vp_ 2023-03-07
|
41
|
-
# def add_tag which
|
42
|
-
# tag = WpTag.iso_get which
|
43
|
-
# # puts!( tag.slug, "Adding tag" ) if DEBUG
|
44
|
-
# Office::EmailConversationTag.find_or_create_by!({
|
45
|
-
# email_conversation_id: id,
|
46
|
-
# wp_term_id: tag.id,
|
47
|
-
# })
|
48
|
-
# end
|
49
|
-
def add_tag which
|
50
|
-
::EmailtagTie.create!({ emailtag: which, email_conversation: self })
|
51
|
-
end
|
52
|
-
|
53
|
-
# def remove_tag which
|
54
|
-
# tag = WpTag.iso_get which
|
55
|
-
# # puts!( tag.slug, "Removing tag" ) if DEBUG
|
56
|
-
# Office::EmailConversationTag.where({
|
57
|
-
# email_conversation_id: id,
|
58
|
-
# wp_term_id: tag.id,
|
59
|
-
# }).first&.delete
|
60
|
-
# end
|
61
|
-
def remove_tag which
|
62
|
-
::EmailtagTie.find_by({ emailtag: which, email_conversation: self }).delete
|
63
|
-
end
|
64
|
-
def rmtag which; remove_tag which; end
|
65
|
-
|
66
|
-
# def in_emailtag? which
|
67
|
-
# tag = WpTag.iso_get( which )
|
68
|
-
# email_conversation_tags.where({ wp_term_id: tag.id }).present?
|
69
|
-
# end
|
70
|
-
def in_emailtag? which
|
71
|
-
if which.class == String
|
72
|
-
which = Office::Emailtag.find_by({ slug: which })
|
73
|
-
end
|
74
|
-
!!::EmailtagTie.where({ emailtag: which, email_conversation: self }).first
|
75
|
-
end
|
76
|
-
|
77
|
-
# def self.in_emailtag which
|
78
|
-
# tag = WpTag.iso_get( which )
|
79
|
-
# email_conversation_tags = Office::EmailConversationTag.where({ wp_term_id: tag.id })
|
80
|
-
# where({ :id.in => email_conversation_tags.map(&:email_conversation_id) })
|
81
|
-
# end
|
82
|
-
def self.in_emailtag which, page: 1, per: 25
|
83
|
-
conv_ids = ::EmailtagTie.find_by({ emailtag: which }).map( &:email_conversation_id )
|
84
|
-
Conv.where({ id: conv_ids }).order_by({ updated_at: :desc }).page( page ).per( per )
|
85
|
-
end
|
86
|
-
|
87
|
-
# def self.not_in_emailtag which
|
88
|
-
# tag = WpTag.iso_get( which )
|
89
|
-
# email_conversation_tags = Office::EmailConversationTag.where({ wp_term_id: tag.id })
|
90
|
-
# where({ :id.nin => email_conversation_tags.map(&:email_conversation_id) })
|
91
|
-
# end
|
92
|
-
def self.not_in_emailtag which, page: 1, per: 25
|
93
|
-
conv_ids = ::EmailtagTie.find_by({ emailtag: which }).map( &:email_conversation_id )
|
94
|
-
Conv.where({ :id.nin => conv_ids }).order_by({ updated_at: :desc }).page( page ).per( per )
|
95
|
-
end
|
96
|
-
|
97
|
-
|
98
|
-
|
99
|
-
|
100
|
-
|
101
|
-
end
|
102
|
-
Conv = Office::EmailConversation
|
@@ -1,11 +0,0 @@
|
|
1
|
-
|
2
|
-
class Office::EmailConversationLead
|
3
|
-
include Mongoid::Document
|
4
|
-
include Mongoid::Timestamps
|
5
|
-
|
6
|
-
belongs_to :email_conversation, class_name: 'Office::EmailConversation'
|
7
|
-
|
8
|
-
field :lead_id, type: :integer
|
9
|
-
validates :lead_id, uniqueness: { scope: :email_conversation_id }, presence: true
|
10
|
-
|
11
|
-
end
|
@@ -1,14 +0,0 @@
|
|
1
|
-
|
2
|
-
class Office::EmailConversationTag
|
3
|
-
include Mongoid::Document
|
4
|
-
include Mongoid::Timestamps
|
5
|
-
|
6
|
-
belongs_to :email_conversation, class_name: 'Office::EmailConversation'
|
7
|
-
|
8
|
-
field :wp_term_id, type: :integer
|
9
|
-
validates :wp_term_id, uniqueness: { scope: :email_conversation_id }, presence: true
|
10
|
-
index({ wp_term_id: -1 })
|
11
|
-
index({ wp_term_id: -1, latest_at: -1 })
|
12
|
-
|
13
|
-
|
14
|
-
end
|
data/lib/office/email_filter.rb
DELETED
@@ -1,45 +0,0 @@
|
|
1
|
-
|
2
|
-
##
|
3
|
-
## 2023-03-04 _vp_ When I receive one.
|
4
|
-
##
|
5
|
-
class Office::EmailFilter
|
6
|
-
include Mongoid::Document
|
7
|
-
include Mongoid::Timestamps
|
8
|
-
|
9
|
-
field :from_regex
|
10
|
-
field :from_exact
|
11
|
-
field :subject_regex
|
12
|
-
field :subject_exact
|
13
|
-
field :body_regex
|
14
|
-
field :body_exact
|
15
|
-
|
16
|
-
|
17
|
-
KIND_AUTORESPOND_TMPL = 'autorespond-template'
|
18
|
-
KIND_AUTORESPOND_EACT = 'autorespond-email-action'
|
19
|
-
KIND_REMOVE_TAG = 'remove-tag'
|
20
|
-
KIND_ADD_TAG = 'add-tag'
|
21
|
-
KIND_DESTROY_SCHS = 'destroy-schs'
|
22
|
-
|
23
|
-
KIND_AUTORESPOND = 'autorespond' # @deprecated, DO NOT USE!
|
24
|
-
KIND_DELETE = 'delete' # @deprecated, use add-tag
|
25
|
-
KIND_SKIP_INBOX = 'skip-inbox' # @deprecated, use remove-tag
|
26
|
-
|
27
|
-
KINDS = [ nil, KIND_AUTORESPOND_TMPL, KIND_AUTORESPOND_EACT, KIND_ADD_TAG, KIND_REMOVE_TAG, KIND_DESTROY_SCHS]
|
28
|
-
field :kind
|
29
|
-
|
30
|
-
STATE_ACTIVE = 'active'
|
31
|
-
STATE_INACTIVE = 'inactive'
|
32
|
-
STATES = [ STATE_ACTIVE, STATE_INACTIVE ]
|
33
|
-
field :state, type: :string, default: STATE_ACTIVE
|
34
|
-
scope :active, ->{ where( state: STATE_ACTIVE ) }
|
35
|
-
|
36
|
-
belongs_to :email_template, class_name: 'Ish::EmailTemplate', optional: true
|
37
|
-
belongs_to :email_action, class_name: 'Office::EmailAction', optional: true
|
38
|
-
|
39
|
-
field :wp_term_id, type: :integer
|
40
|
-
def category
|
41
|
-
self.wp_term_id && WpTag.find( self.wp_term_id )
|
42
|
-
end
|
43
|
-
|
44
|
-
end
|
45
|
-
|
data/lib/office/email_message.rb
DELETED
@@ -1,192 +0,0 @@
|
|
1
|
-
|
2
|
-
require 'action_view'
|
3
|
-
|
4
|
-
##
|
5
|
-
## When I receive one.
|
6
|
-
##
|
7
|
-
class Office::EmailMessage
|
8
|
-
include Mongoid::Document
|
9
|
-
include Mongoid::Timestamps
|
10
|
-
|
11
|
-
field :raw, type: :string
|
12
|
-
def the_mail
|
13
|
-
Mail.new( raw )
|
14
|
-
end
|
15
|
-
|
16
|
-
field :message_id, type: :string # MESSAGE-ID
|
17
|
-
validates_uniqueness_of :message_id
|
18
|
-
index({ message_id: 1 }, { unique: true, name: "id_idx" })
|
19
|
-
|
20
|
-
field :in_reply_to_id, type: :string
|
21
|
-
|
22
|
-
field :object_key, type: :string ## aka 'filename', use with bucket name + prefix. I need this!
|
23
|
-
# validates_presence_of :object_key
|
24
|
-
field :object_path, type: :string ## A routable s3 url
|
25
|
-
|
26
|
-
field :subject
|
27
|
-
field :part_html
|
28
|
-
field :part_txt
|
29
|
-
|
30
|
-
def lead
|
31
|
-
Lead.find_by email: from
|
32
|
-
end
|
33
|
-
|
34
|
-
field :from, type: :string
|
35
|
-
field :froms, type: Array, default: []
|
36
|
-
field :to, type: :string
|
37
|
-
field :tos, type: Array, default: []
|
38
|
-
field :cc, type: :string
|
39
|
-
field :ccs, type: Array, default: []
|
40
|
-
def all_ccs; (tos||[]) + (ccs||[]) + (froms||[]); end
|
41
|
-
field :bcc, type: :string
|
42
|
-
field :bccs, type: Array, default: []
|
43
|
-
|
44
|
-
field :logs, type: Array, default: []
|
45
|
-
|
46
|
-
field :date, type: DateTime
|
47
|
-
def received_at
|
48
|
-
date
|
49
|
-
end
|
50
|
-
|
51
|
-
belongs_to :email_conversation, class_name: 'Office::EmailConversation'
|
52
|
-
def conv
|
53
|
-
email_conversation
|
54
|
-
end
|
55
|
-
|
56
|
-
has_many :email_attachments, class_name: 'Office::EmailAttachment', inverse_of: :email_message
|
57
|
-
has_many :asset3ds, class_name: 'Gameui::Asset3d', inverse_of: :email_message
|
58
|
-
has_many :attachments, class_name: 'Photo'
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
def apply_filter filter
|
63
|
-
case filter.kind
|
64
|
-
|
65
|
-
when ::Office::EmailFilter::KIND_DESTROY_SCHS
|
66
|
-
conv.add_tag ::WpTag::TRASH
|
67
|
-
conv.remove_tag ::WpTag::INBOX
|
68
|
-
lead.schs.each do |sch|
|
69
|
-
sch.update_attributes({ state: ::Sch::STATE_TRASH })
|
70
|
-
end
|
71
|
-
|
72
|
-
when ::Office::EmailFilter::KIND_ADD_TAG
|
73
|
-
conv.add_tag filter.wp_term_id
|
74
|
-
if ::WpTag::TRASH == ::WpTag.find( filter.wp_term_id ).slug
|
75
|
-
conv.remove_tag ::WpTag::INBOX
|
76
|
-
end
|
77
|
-
|
78
|
-
when ::Office::EmailFilter::KIND_REMOVE_TAG
|
79
|
-
conv.remove_tag filter.wp_term_id
|
80
|
-
|
81
|
-
when ::Office::EmailFilter::KIND_AUTORESPOND_TMPL
|
82
|
-
Ish::EmailContext.create({
|
83
|
-
email_template: filter.email_template,
|
84
|
-
lead_id: lead.id,
|
85
|
-
send_at: Time.now + 22.minutes,
|
86
|
-
})
|
87
|
-
|
88
|
-
when ::Office::EmailFilter::KIND_AUTORESPOND_EACT
|
89
|
-
::Sch.create({
|
90
|
-
email_action: filter.email_action,
|
91
|
-
state: ::Sch::STATE_ACTIVE,
|
92
|
-
lead_id: lead.id,
|
93
|
-
perform_at: Time.now + 22.minutes,
|
94
|
-
})
|
95
|
-
|
96
|
-
else
|
97
|
-
raise "unknown filter kind: #{filter.kind}"
|
98
|
-
end
|
99
|
-
end
|
100
|
-
|
101
|
-
## From: https://stackoverflow.com/questions/24672834/how-do-i-remove-emoji-from-string/24673322
|
102
|
-
def self.strip_emoji(text)
|
103
|
-
text = '' if text.blank?
|
104
|
-
text = text.force_encoding('utf-8').encode
|
105
|
-
clean = ""
|
106
|
-
|
107
|
-
# symbols & pics
|
108
|
-
regex = /[\u{1f300}-\u{1f5ff}]/
|
109
|
-
clean = text.gsub regex, ""
|
110
|
-
|
111
|
-
# enclosed chars
|
112
|
-
regex = /[\u{2500}-\u{2BEF}]/ # I changed this to exclude chinese char
|
113
|
-
clean = clean.gsub regex, ""
|
114
|
-
|
115
|
-
# emoticons
|
116
|
-
regex = /[\u{1f600}-\u{1f64f}]/
|
117
|
-
clean = clean.gsub regex, ""
|
118
|
-
|
119
|
-
#dingbats
|
120
|
-
regex = /[\u{2702}-\u{27b0}]/
|
121
|
-
clean = clean.gsub regex, ""
|
122
|
-
end
|
123
|
-
|
124
|
-
## For recursive parts of type `related`.
|
125
|
-
## Content dispositions:
|
126
|
-
# "inline; creation-date=\"Tue, 11 Apr 2023 19:39:42 GMT\"; filename=image005.png; modification-date=\"Tue, 11 Apr 2023 19:47:53 GMT\"; size=14916",
|
127
|
-
#
|
128
|
-
## Content Types:
|
129
|
-
# "application/pdf; name=\"Securities Forward Agreement -- HaulHub Inc -- Victor Pudeyev -- 2021-10-26.docx.pdf\""
|
130
|
-
# "image/jpeg; name=TX_DL_2.jpg"
|
131
|
-
# "image/png; name=image005.png"
|
132
|
-
# "multipart/alternative; boundary=_000_BL0PR10MB2913C560ADE059F0AB3A6D11829A9BL0PR10MB2913namp_",
|
133
|
-
# "text/html; charset=utf-8"
|
134
|
-
# "text/plain; charset=UTF-8"
|
135
|
-
# "text/calendar; charset=utf-8; method=REQUEST"
|
136
|
-
def churn_subpart part
|
137
|
-
if part.content_disposition&.include?('attachment')
|
138
|
-
## @TODO: attachments !
|
139
|
-
;
|
140
|
-
else
|
141
|
-
if part.content_type.include?("multipart/related") ||
|
142
|
-
part.content_type.include?("multipart/alternative")
|
143
|
-
|
144
|
-
part.parts.each do |subpart|
|
145
|
-
churn_subpart( subpart )
|
146
|
-
end
|
147
|
-
else
|
148
|
-
# attachment = Office::EmailAttachment.new({
|
149
|
-
# content: part.decoded,
|
150
|
-
# content_type: part.content_type,
|
151
|
-
# email_message: self,
|
152
|
-
# })
|
153
|
-
# attachment.save
|
154
|
-
|
155
|
-
if part.content_type.include?('text/html')
|
156
|
-
self.part_html = part.decoded
|
157
|
-
|
158
|
-
elsif part.content_type.include?("text/plain")
|
159
|
-
self.part_txt = part.decoded
|
160
|
-
|
161
|
-
elsif part.content_type.include?("text/calendar")
|
162
|
-
;
|
163
|
-
elsif part.content_type.include?("application/pdf")
|
164
|
-
;
|
165
|
-
elsif part.content_type.include?("image/jpeg")
|
166
|
-
;
|
167
|
-
elsif part.content_type.include?("image/png")
|
168
|
-
;
|
169
|
-
|
170
|
-
else
|
171
|
-
self.logs.push "444 No action for a part with content_type #{part.content_type}"
|
172
|
-
|
173
|
-
end
|
174
|
-
end
|
175
|
-
end
|
176
|
-
end
|
177
|
-
|
178
|
-
|
179
|
-
def body_sanitized
|
180
|
-
ActionView::Base.full_sanitizer.sanitize( part_html||'' ).squish
|
181
|
-
end
|
182
|
-
def preview_str
|
183
|
-
body_sanitized[0..200]
|
184
|
-
end
|
185
|
-
|
186
|
-
|
187
|
-
end
|
188
|
-
::Msg = Office::EmailMessage
|
189
|
-
|
190
|
-
|
191
|
-
|
192
|
-
|
@@ -1,22 +0,0 @@
|
|
1
|
-
|
2
|
-
##
|
3
|
-
## Only object_key, object_path, no validations.
|
4
|
-
##
|
5
|
-
class Office::EmailMessageStub
|
6
|
-
include Mongoid::Document
|
7
|
-
include Mongoid::Timestamps
|
8
|
-
|
9
|
-
STATE_PENDING = 'state_pending'
|
10
|
-
STATE_PROCESSED = 'state_processed'
|
11
|
-
STATES = [ STATE_PENDING, STATE_PROCESSED ]
|
12
|
-
field :state, type: :string, default: STATE_PENDING
|
13
|
-
|
14
|
-
field :object_key, type: :string ## aka 'filename', use with bucket name + prefix
|
15
|
-
validates :object_key, presence: true, uniqueness: true
|
16
|
-
|
17
|
-
# field :object_path, type: :string ## A routable s3 url ## @TODO: remove this field. _vp_ 2023-03-07
|
18
|
-
|
19
|
-
# field :wp_term_ids, type: :array, default: []
|
20
|
-
|
21
|
-
end
|
22
|
-
MsgStub = EMS = Office::EmailMessageStub
|
data/lib/office/emailtag.rb
DELETED
@@ -1,27 +0,0 @@
|
|
1
|
-
|
2
|
-
class Office::Emailtag
|
3
|
-
include Mongoid::Document
|
4
|
-
include Mongoid::Timestamps
|
5
|
-
|
6
|
-
# field :name
|
7
|
-
# validates :name, presence: true
|
8
|
-
|
9
|
-
field :slug
|
10
|
-
validates :slug, presence: true
|
11
|
-
|
12
|
-
INBOX = 'inbox'
|
13
|
-
TRASH = 'trash'
|
14
|
-
EMAILTAGS = [ INBOX, TRASH ]
|
15
|
-
|
16
|
-
def self.inbox
|
17
|
-
Office::Emailtag.find_by({ slug: INBOX })
|
18
|
-
end
|
19
|
-
|
20
|
-
def self.trash
|
21
|
-
Office::Emailtag.find_by({ slug: TRASH })
|
22
|
-
end
|
23
|
-
|
24
|
-
has_many :emailtag_ties, class_name: 'Office::EmailtagEmailConversation'
|
25
|
-
|
26
|
-
end
|
27
|
-
Tag = Office::Emailtag
|
@@ -1,10 +0,0 @@
|
|
1
|
-
|
2
|
-
class Office::EmailtagEmailConversation
|
3
|
-
include Mongoid::Document
|
4
|
-
include Mongoid::Timestamps
|
5
|
-
|
6
|
-
belongs_to :emailtag, class_name: 'Office::Emailtag'
|
7
|
-
belongs_to :email_conversation, class_name: 'Office::EmailConversation'
|
8
|
-
|
9
|
-
end
|
10
|
-
EmailtagTie = Office::EmailtagEmailConversation
|
data/lib/office/lead_action.rb
DELETED
@@ -1,24 +0,0 @@
|
|
1
|
-
|
2
|
-
##
|
3
|
-
## The obfuscated action
|
4
|
-
##
|
5
|
-
class Office::LeadAction
|
6
|
-
include Mongoid::Document
|
7
|
-
include Mongoid::Timestamps
|
8
|
-
|
9
|
-
belongs_to :lead_action_template, class_name: '::Office::LeadActionTemplate', inverse_of: :lead_actions, foreign_key: :tmpl_id
|
10
|
-
def tmpl
|
11
|
-
lead_action_template
|
12
|
-
end
|
13
|
-
|
14
|
-
field :lead_id, type: :integer
|
15
|
-
validates :lead_id, presence: true
|
16
|
-
def lead
|
17
|
-
Lead.find( lead_id )
|
18
|
-
end
|
19
|
-
|
20
|
-
field :params, type: Object, default: '{}'
|
21
|
-
|
22
|
-
|
23
|
-
end
|
24
|
-
|
@@ -1,47 +0,0 @@
|
|
1
|
-
|
2
|
-
##
|
3
|
-
##
|
4
|
-
class Office::LeadActionTemplate
|
5
|
-
include Mongoid::Document
|
6
|
-
include Mongoid::Timestamps
|
7
|
-
|
8
|
-
has_many :lead_actions, class_name: '::Office::LeadAction', inverse_of: :lead_action_templates
|
9
|
-
|
10
|
-
field :slug
|
11
|
-
validates :slug, presence: true
|
12
|
-
|
13
|
-
field :action_exe, type: :string
|
14
|
-
# validates :action_exe, presence: true
|
15
|
-
|
16
|
-
field :config_json, type: Object, default: '{}'
|
17
|
-
|
18
|
-
field :kind, type: :string
|
19
|
-
KIND_UNSUBSCRIBE_TEMPLATE = 'kind-unsubscribe-template'
|
20
|
-
KIND_UNSUBSCRIBE_CAMPAIGN = 'kind-unsubscribe-campaign'
|
21
|
-
KINDS = [ KIND_UNSUBSCRIBE_TEMPLATE, KIND_UNSUBSCRIBE_CAMPAIGN ]
|
22
|
-
|
23
|
-
def to_s
|
24
|
-
"OLAT:#{slug}"
|
25
|
-
end
|
26
|
-
|
27
|
-
def unsubscribe_from_campaign
|
28
|
-
end
|
29
|
-
|
30
|
-
def unsubscribe_from_template
|
31
|
-
template = EmailTemplate.find( ctx[:template_id] )
|
32
|
-
subject = "Lead #{lead.full_name} unsubscribed from template #{template.slug}"
|
33
|
-
out = Mailer.notify( 'poxlovi@gmail.com', subject )
|
34
|
-
Rails.env.production? ? out.deliver_later : out.deliver_now
|
35
|
-
Office::Unsubscribe.create({
|
36
|
-
lead_id: lead_id,
|
37
|
-
template_id: config_json['template_id'],
|
38
|
-
})
|
39
|
-
end
|
40
|
-
|
41
|
-
def self.list
|
42
|
-
[ [nil,nil] ] + all.map { |i| [ i.slug, i.id.to_s ] }
|
43
|
-
end
|
44
|
-
|
45
|
-
|
46
|
-
end
|
47
|
-
OLAT = Office::LeadActionTemplate
|
@@ -1,62 +0,0 @@
|
|
1
|
-
|
2
|
-
##
|
3
|
-
## 2023-03-04 _vp_ An instance of an EmailAction.
|
4
|
-
##
|
5
|
-
class Office::ScheduledEmailAction
|
6
|
-
include Mongoid::Document
|
7
|
-
include Mongoid::Timestamps
|
8
|
-
include Mongoid::Paranoia
|
9
|
-
store_in collection: 'office_scheduled_email_actions'
|
10
|
-
|
11
|
-
field :lead_id, type: :integer
|
12
|
-
def lead
|
13
|
-
Lead.find( lead_id )
|
14
|
-
end
|
15
|
-
|
16
|
-
STATE_ACTIVE = 'active'
|
17
|
-
STATE_INACTIVE = 'inactive'
|
18
|
-
STATE_TRASH = 'trash'
|
19
|
-
STATE_UNSUBSCRIBED = 'unsubscribed'
|
20
|
-
STATES = [ STATE_ACTIVE, STATE_INACTIVE, STATE_UNSUBSCRIBED, STATE_TRASH ]
|
21
|
-
field :state, type: :string
|
22
|
-
scope :active, ->{ where( state: STATE_ACTIVE ) }
|
23
|
-
|
24
|
-
belongs_to :email_action, class_name: '::Office::EmailAction'
|
25
|
-
validates :email_action, uniqueness: { scope: :lead_id }
|
26
|
-
def act; email_action; end
|
27
|
-
def act= a; email_action= a; end
|
28
|
-
|
29
|
-
has_many :email_contexts, class_name: '::Ish::EmailContext'
|
30
|
-
def ctxs; email_contexts; end
|
31
|
-
|
32
|
-
field :perform_at, type: :time
|
33
|
-
|
34
|
-
def send_and_roll
|
35
|
-
sch = self
|
36
|
-
sch.update({ state: Sch::STATE_INACTIVE })
|
37
|
-
|
38
|
-
# send now
|
39
|
-
ctx = Ctx.create!({
|
40
|
-
email_template_id: sch.act.tmpl.id,
|
41
|
-
from_email: sch.act.tmpl.from_email,
|
42
|
-
lead_id: sch.lead.id,
|
43
|
-
scheduled_email_action_id: sch.act.id,
|
44
|
-
send_at: Time.now,
|
45
|
-
subject: sch.act.tmpl.subject,
|
46
|
-
})
|
47
|
-
|
48
|
-
# schedule next actions & update the action
|
49
|
-
sch.act.ties.each do |tie|
|
50
|
-
next_sch = Sch.find_or_initialize_by({
|
51
|
-
lead_id: sch.lead_id,
|
52
|
-
email_action_id: tie.next_email_action.id,
|
53
|
-
})
|
54
|
-
next_sch.perform_at = eval(tie.next_at_exe)
|
55
|
-
next_sch.state = Sch::STATE_ACTIVE
|
56
|
-
next_sch.save!
|
57
|
-
end
|
58
|
-
end
|
59
|
-
|
60
|
-
end
|
61
|
-
::Sch = Office::ScheduledEmailAction
|
62
|
-
|