commit 3a477f8b0f58503d00ab3cb5890e9b423fc6a622
parent 6ef7c0a082c03f65ebfa7c329c5e845029349625
Author: Fredrik <moi@knutsen.co>
Date: Mon, 29 Oct 2018 17:33:30 +0000
Merge pull request #6 from Demonstrandum/devel
Update to using MongoDB
Diffstat:
8 files changed, 95 insertions(+), 71 deletions(-)
diff --git a/.gitignore b/.gitignore
@@ -0,0 +1,41 @@
+# gem
+*.gem
+
+# Shh, web stuff
+tmp/
+log/
+
+## System and release files ##
+# OS files
+.DS_Store
+.DS_Store?
+._*
+.Spotlight-V100
+.Trashes
+ehthumbs.db
+Thumbs.db
+*.swp
+*.ini
+
+# Compiled files
+*.com
+*.class
+*.dll
+*.exe
+*.o
+*.so
+
+# Packages
+*.7z
+*.dmg
+*.gz
+*.iso
+*.jar
+*.rar
+*.tar
+*.zip
+
+# Debug logs and databases
+*.log
+*.sql
+*.sqlite
diff --git a/Gemfile b/Gemfile
@@ -5,3 +5,4 @@ gem 'rack', '~> 2.0', '>= 2.0.5'
gem 'rack-ssl', '~> 1.4'
gem 'sinatra', '~> 2.0', '>= 2.0.1'
gem 'json'
+gem 'mongo'
diff --git a/Gemfile.lock b/Gemfile.lock
@@ -1,9 +1,12 @@
GEM
remote: https://rubygems.org/
specs:
+ bson (4.3.0)
daemons (1.2.6)
eventmachine (1.2.7)
json (2.1.0)
+ mongo (2.6.2)
+ bson (>= 4.3.0, < 5.0.0)
mustermann (1.0.3)
rack (2.0.5)
rack-protection (2.0.4)
@@ -15,7 +18,6 @@ GEM
rack (~> 2.0)
rack-protection (= 2.0.4)
tilt (~> 2.0)
- symbolized (0.0.1)
thin (1.7.2)
daemons (~> 1.0, >= 1.0.9)
eventmachine (~> 1.0, >= 1.0.4)
@@ -27,10 +29,10 @@ PLATFORMS
DEPENDENCIES
json
+ mongo
rack (~> 2.0, >= 2.0.5)
rack-ssl (~> 1.4)
sinatra (~> 2.0, >= 2.0.1)
- symbolized
thin
BUNDLED WITH
diff --git a/now.json b/now.json
@@ -1,5 +1,8 @@
{
"name": "Veto",
"alias": "veto.vote",
- "type": "docker"
+ "type": "docker",
+ "env": {
+ "MONGO_DB": "@mongo_url_secret"
+ }
}
diff --git a/public/styles.css b/public/styles.css
@@ -217,6 +217,10 @@ h3 {
border-bottom: 2px solid;
}
+.issues h3 {
+ color: inherit;
+}
+
.issues .show {
max-height: 300px;
opacity: 1;
@@ -225,7 +229,7 @@ h3 {
.issues .error {
background: #ffc8b3;
border-color: #ff5436;
- color: #800;
+ color: #800 !important;
}
.issues .error p {
@@ -236,7 +240,7 @@ h3 {
.issues .warning {
background: #ffeab3;
border-color: #ffc136;
- color: #885a00;
+ color: #885a00 !important;
}
.issues .warning p {
diff --git a/server.rb b/server.rb
@@ -1,4 +1,4 @@
-require 'net/http'
+require 'mongo'
require 'json'
require 'sinatra'
@@ -11,57 +11,24 @@ enable :sessions
before { request.path_info.sub! %r{/$}, "" }
-$INDIFFERENT = proc do |h, k|
- case k
- when String then sym = k.to_sym; h[sym] if h.key?(sym)
- when Symbol then str = k.to_s; h[str] if h.key?(str)
- end
-end
-
-$polls = {
- :'this-is-a-poll-name' => {
- :name => 'This is a poll name',
- :votes => {},
- :alt => true,
- :voters => []
- }
-} # Example.
-
-$JSON_ID = '1arifg'
-$JSON_BASE = 'https://api.myjson.com'
+# ENV['MONGO_DB'] variable with Now secrets, or just in your shell if local.
+CLIENT = Mongo::Client.new "#{ENV['MONGO_DB']}/Veto"
+POLLS = CLIENT[:polls]
-String.class_eval { def to_uri; URI(self); end }
-$polls.default_proc = $INDIFFERENT
-
-def request_json
- puts "[!!] Requesting JSON, ID: #{$JSON_ID}"
- response = Net::HTTP.get "#{$JSON_BASE}/bins/#{$JSON_ID}".to_uri
- $polls = JSON.parse response, {:symbolize_names => true}
- $polls.default_proc = $INDIFFERENT
- pp $polls
-end
-
-def save_json
- puts "[!!] Saving JSON, ID: #{$JSON_ID}"
- uri = "#{$JSON_BASE}/bins/#{$JSON_ID}".to_uri
- puts "[!!]\tURI: #{uri}"
- req = Net::HTTP::Put.new uri
- req.set_content_type 'application/json'
- req.body = $polls.to_json
- res = Net::HTTP.start(uri.hostname, uri.port, use_ssl: true) { |http| http.request req }
- puts "[!!]\tResponse: #{res.inspect}"
+def poll_exist? code
+ POLLS.find({:code => code}).to_a.size > 0
end
-request_json # Initial JSON retrieval
-
def make_poll code, name, alt
- $polls[code] = {
+ alt = alt.to_s == 'true'
+ poll = {
+ :code => code,
:name => name,
:votes => {},
:alt => alt,
:voters => []
}
- save_json
+ POLLS.insert_one poll
end
$HEAD_TAGS = <<-HTML
@@ -97,7 +64,7 @@ get '/share/:code' do
end
post '/new' do
- return nil if $polls.keys.include? params[:code]
+ return nil if poll_exist? params[:code]
make_poll(
params[:code],
@@ -105,47 +72,45 @@ post '/new' do
params[:alt])
params[:primary].each do |option|
- $polls[params[:code]][:votes][option] = {
- :number => 0,
- :primary => true
- }
+ POLLS.update_one({:code => params[:code]}, {
+ :"$set" => {
+ :"votes.#{option}" => {
+ :number => 0,
+ :primary => true
+ }
+ }
+ })
end
- save_json
end
get '/poll/:poll' do
- unless $polls.keys.map(&:to_s).include? params[:poll]
+ unless poll_exist? params[:poll]
return "This poll has not been created/does not exist!"
end
local = {:code => params[:poll], :head_tags => $HEAD_TAGS}
- local.merge! $polls[params[:poll]]
+ local.merge! Hash.from_bson POLLS.find({:code => params[:poll]}).first.to_bson
erb :poll, :locals => local
end
post '/poll/:poll/cast' do
- return nil if $polls[params[:poll]][:voters].include? request.ip
- $polls[params[:poll]][:voters].push request.ip
+ return nil if POLLS.find(:"$and" => [{:code => params[:poll]}, {:voters => request.ip}]).to_a.size > 0
+ POLLS.update_one({:code => params[:poll]}, {:"$push" => {:voters => request.ip}})
- if $polls[params[:poll]][:votes].keys.include? params[:vote]
- $polls[params[:poll]][:votes][params[:vote]][:number] += 1
+ if POLLS.find({ :"votes.#{params[:vote]}" => {"$exists": true} })
+ POLLS.update_one({:code => params[:poll]}, { :"$inc" => { :"votes.#{params[:vote]}.number" => 1 } })
else
- $polls[params[:poll]][:votes][params[:vote]] = {
+ POLLS.update_one({:code => params[:poll]}, {:"$set" => {:"vote.#{params[:vote]}" => {
:number => 1,
:primary => false
- }
+ }}})
end
- save_json
end
get '/poll/:poll/votes.json' do
- $polls[params[:poll]][:votes].to_json
+ (Hash.from_bson POLLS.find({:code => params[:poll]}).to_a.first.to_bson)[:votes].to_json
end
get '/polls.json' do
- $polls.keys.map(&:to_s).to_json
-end
-
-get '/exported.json' do
- $polls.to_json
+ POLLS.find.to_a.map { |doc| doc[:code] }.to_json
end
diff --git a/server.rb b/server.rb.old
diff --git a/views/index.erb b/views/index.erb
@@ -139,12 +139,20 @@
}
});
+ $(document).on('keypress', '.editor', key => {
+ if (key.which === 13 || key.which === 10) {
+ key.preventDefault();
+ save();
+ editing = NaN;
+ }
+ });
+
$("#addition").on('keypress', key => {
let value = $("#addition").val().trim();
let values = Array(...$('#options li span').map((i, e) => e.innerHTML));
- if (key.which === 13) {
- save();
+ if (key.which === 13 || key.which === 10) {
key.preventDefault();
+ save();
if (value.length === 0) {
return $('#addition').attention();
}