diff --git a/Gemfile b/Gemfile index 5b379c6c..eb310d43 100644 --- a/Gemfile +++ b/Gemfile @@ -1,7 +1,7 @@ -source 'http://rubygems.org' +source 'https://rubygems.org' ruby '3.1.4' -gem 'rails', '= 7.0.7.1' +gem 'rails', '~> 7.1', '>= 7.1.1' # The HTTP server running the Rails instance. gem 'puma', '~> 6.3', '>= 6.3.1' @@ -54,6 +54,9 @@ gem 'letter_opener', '~> 1.8', '>= 1.8.1', group: :development # For parallel API calls. gem 'parallel', '~> 1.23' +# For miscellaneous HTTP requests. +gem "httparty", "~> 0.21.0" + # For debugging. gem 'web-console', '~> 4.2', group: :development @@ -62,9 +65,3 @@ gem 'record_tag_helper', '~> 1.0', '>= 1.0.1' # Reduces boot times through caching; required in config/boot.rb gem 'bootsnap', '~> 1.16', require: false - -# For testing. -group :test do - gem 'factory_girl_rails', '~> 4.9' - gem 'rspec-rails', '~> 2.0.0.beta.22' -end diff --git a/Gemfile.lock b/Gemfile.lock index a99a9eff..d71bd61c 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -5,72 +5,80 @@ GIT RocketAMF (1.0.0) GEM - remote: http://rubygems.org/ + remote: https://rubygems.org/ specs: - actioncable (7.0.7.1) - actionpack (= 7.0.7.1) - activesupport (= 7.0.7.1) + actioncable (7.1.1) + actionpack (= 7.1.1) + activesupport (= 7.1.1) nio4r (~> 2.0) websocket-driver (>= 0.6.1) - actionmailbox (7.0.7.1) - actionpack (= 7.0.7.1) - activejob (= 7.0.7.1) - activerecord (= 7.0.7.1) - activestorage (= 7.0.7.1) - activesupport (= 7.0.7.1) + zeitwerk (~> 2.6) + actionmailbox (7.1.1) + actionpack (= 7.1.1) + activejob (= 7.1.1) + activerecord (= 7.1.1) + activestorage (= 7.1.1) + activesupport (= 7.1.1) mail (>= 2.7.1) net-imap net-pop net-smtp - actionmailer (7.0.7.1) - actionpack (= 7.0.7.1) - actionview (= 7.0.7.1) - activejob (= 7.0.7.1) - activesupport (= 7.0.7.1) + actionmailer (7.1.1) + actionpack (= 7.1.1) + actionview (= 7.1.1) + activejob (= 7.1.1) + activesupport (= 7.1.1) mail (~> 2.5, >= 2.5.4) net-imap net-pop net-smtp - rails-dom-testing (~> 2.0) - actionpack (7.0.7.1) - actionview (= 7.0.7.1) - activesupport (= 7.0.7.1) - rack (~> 2.0, >= 2.2.4) + rails-dom-testing (~> 2.2) + actionpack (7.1.1) + actionview (= 7.1.1) + activesupport (= 7.1.1) + nokogiri (>= 1.8.5) + rack (>= 2.2.4) + rack-session (>= 1.0.1) rack-test (>= 0.6.3) - rails-dom-testing (~> 2.0) - rails-html-sanitizer (~> 1.0, >= 1.2.0) - actiontext (7.0.7.1) - actionpack (= 7.0.7.1) - activerecord (= 7.0.7.1) - activestorage (= 7.0.7.1) - activesupport (= 7.0.7.1) + rails-dom-testing (~> 2.2) + rails-html-sanitizer (~> 1.6) + actiontext (7.1.1) + actionpack (= 7.1.1) + activerecord (= 7.1.1) + activestorage (= 7.1.1) + activesupport (= 7.1.1) globalid (>= 0.6.0) nokogiri (>= 1.8.5) - actionview (7.0.7.1) - activesupport (= 7.0.7.1) + actionview (7.1.1) + activesupport (= 7.1.1) builder (~> 3.1) - erubi (~> 1.4) - rails-dom-testing (~> 2.0) - rails-html-sanitizer (~> 1.1, >= 1.2.0) - activejob (7.0.7.1) - activesupport (= 7.0.7.1) + erubi (~> 1.11) + rails-dom-testing (~> 2.2) + rails-html-sanitizer (~> 1.6) + activejob (7.1.1) + activesupport (= 7.1.1) globalid (>= 0.3.6) - activemodel (7.0.7.1) - activesupport (= 7.0.7.1) - activerecord (7.0.7.1) - activemodel (= 7.0.7.1) - activesupport (= 7.0.7.1) - activestorage (7.0.7.1) - actionpack (= 7.0.7.1) - activejob (= 7.0.7.1) - activerecord (= 7.0.7.1) - activesupport (= 7.0.7.1) + activemodel (7.1.1) + activesupport (= 7.1.1) + activerecord (7.1.1) + activemodel (= 7.1.1) + activesupport (= 7.1.1) + timeout (>= 0.4.0) + activestorage (7.1.1) + actionpack (= 7.1.1) + activejob (= 7.1.1) + activerecord (= 7.1.1) + activesupport (= 7.1.1) marcel (~> 1.0) - mini_mime (>= 1.1.0) - activesupport (7.0.7.1) + activesupport (7.1.1) + base64 + bigdecimal concurrent-ruby (~> 1.0, >= 1.0.2) + connection_pool (>= 2.2.5) + drb i18n (>= 1.6, < 2) minitest (>= 5.1) + mutex_m tzinfo (~> 2.0) addressable (2.8.4) public_suffix (>= 2.0.2, < 6.0) @@ -78,7 +86,9 @@ GEM babel-transpiler (0.7.0) babel-source (>= 4.0, < 6) execjs (~> 2.0) + base64 (0.1.1) bcrypt (3.1.19) + bigdecimal (3.1.4) bindex (0.8.1) bootsnap (1.16.0) msgpack (~> 1.2) @@ -87,7 +97,7 @@ GEM connection_pool (2.2.5) crass (1.0.6) date (3.3.3) - devise (4.9.2) + devise (4.9.3) bcrypt (~> 3.0) orm_adapter (~> 0.1) railties (>= 4.1.0) @@ -95,20 +105,16 @@ GEM warden (~> 1.2.3) devise-encryptable (0.2.0) devise (>= 2.1.0) - diff-lcs (1.2.5) domain_name (0.5.20190701) unf (>= 0.0.5, < 1.0.0) dotenv (2.8.1) dotenv-rails (2.8.1) dotenv (= 2.8.1) railties (>= 3.2) + drb (2.1.1) + ruby2_keywords erubi (1.12.0) execjs (2.5.2) - factory_girl (4.9.0) - activesupport (>= 3.0.0) - factory_girl_rails (4.9.0) - factory_girl (~> 4.9.0) - railties (>= 3.0.0) ffi (1.15.5) globalid (1.2.1) activesupport (>= 6.1) @@ -124,9 +130,16 @@ GEM http-cookie (1.0.5) domain_name (~> 0.5) http_accept_language (2.1.1) + httparty (0.21.0) + mini_mime (>= 1.0.0) + multi_xml (>= 0.5.2) i18n (1.14.1) concurrent-ruby (~> 1.0) - jsbundling-rails (1.1.2) + io-console (0.6.0) + irb (1.8.3) + rdoc + reline (>= 0.3.8) + jsbundling-rails (1.2.1) railties (>= 6.0.0) launchy (2.5.2) addressable (~> 2.8) @@ -141,7 +154,6 @@ GEM net-pop net-smtp marcel (1.0.2) - method_source (1.0.0) mime-types (3.4.1) mime-types-data (~> 3.2015) mime-types-data (3.2023.0218.1) @@ -149,6 +161,8 @@ GEM mini_portile2 (2.8.4) minitest (5.19.0) msgpack (1.7.2) + multi_xml (0.6.0) + mutex_m (0.1.2) mysql2 (0.5.5) net-imap (0.4.2) date @@ -166,6 +180,8 @@ GEM racc (~> 1.4) orm_adapter (0.5.0) parallel (1.23.0) + psych (5.1.1.1) + stringio public_suffix (5.0.3) puma (6.4.0) nio4r (~> 2.0) @@ -173,22 +189,27 @@ GEM rack (2.2.8) rack-attack (6.7.0) rack (>= 1.0, < 4) + rack-session (1.0.1) + rack (< 3) rack-test (2.1.0) rack (>= 1.3) - rails (7.0.7.1) - actioncable (= 7.0.7.1) - actionmailbox (= 7.0.7.1) - actionmailer (= 7.0.7.1) - actionpack (= 7.0.7.1) - actiontext (= 7.0.7.1) - actionview (= 7.0.7.1) - activejob (= 7.0.7.1) - activemodel (= 7.0.7.1) - activerecord (= 7.0.7.1) - activestorage (= 7.0.7.1) - activesupport (= 7.0.7.1) + rackup (1.0.0) + rack (< 3) + webrick + rails (7.1.1) + actioncable (= 7.1.1) + actionmailbox (= 7.1.1) + actionmailer (= 7.1.1) + actionpack (= 7.1.1) + actiontext (= 7.1.1) + actionview (= 7.1.1) + activejob (= 7.1.1) + activemodel (= 7.1.1) + activerecord (= 7.1.1) + activestorage (= 7.1.1) + activesupport (= 7.1.1) bundler (>= 1.15.0) - railties (= 7.0.7.1) + railties (= 7.1.1) rails-dom-testing (2.2.0) activesupport (>= 5.0.0) minitest @@ -196,18 +217,21 @@ GEM rails-html-sanitizer (1.6.0) loofah (~> 2.21) nokogiri (~> 1.14) - rails-i18n (7.0.7) + rails-i18n (7.0.8) i18n (>= 0.7, < 2) railties (>= 6.0.0, < 8) - railties (7.0.7.1) - actionpack (= 7.0.7.1) - activesupport (= 7.0.7.1) - method_source + railties (7.1.1) + actionpack (= 7.1.1) + activesupport (= 7.1.1) + irb + rackup (>= 1.0.0) rake (>= 12.2) - thor (~> 1.0) - zeitwerk (~> 2.5) + thor (~> 1.0, >= 1.2.2) + zeitwerk (~> 2.6) rake (13.0.6) rdiscount (2.2.7.1) + rdoc (6.5.0) + psych (>= 4.0.0) react-rails (2.7.1) babel-transpiler (>= 0.7.0) connection_pool @@ -216,9 +240,11 @@ GEM tilt record_tag_helper (1.0.1) actionview (>= 5) + reline (0.3.9) + io-console (~> 0.5) request_store (1.5.1) rack (>= 1.4) - responders (3.1.0) + responders (3.1.1) actionpack (>= 5.2) railties (>= 5.2) rest-client (2.1.0) @@ -226,18 +252,7 @@ GEM http-cookie (>= 1.0.2, < 2.0) mime-types (>= 1.16, < 4.0) netrc (~> 0.8) - rspec (2.0.1) - rspec-core (~> 2.0.1) - rspec-expectations (~> 2.0.1) - rspec-mocks (~> 2.0.1) - rspec-core (2.0.1) - rspec-expectations (2.0.1) - diff-lcs (>= 1.1.2) - rspec-mocks (2.0.1) - rspec-core (~> 2.0.1) - rspec-expectations (~> 2.0.1) - rspec-rails (2.0.1) - rspec (~> 2.0.0) + ruby2_keywords (0.0.5) sanitize (6.0.2) crass (~> 1.0.2) nokogiri (>= 1.12.0) @@ -258,6 +273,7 @@ GEM actionpack (>= 5.2) activesupport (>= 5.2) sprockets (>= 3.0.0) + stringio (3.0.8) temple (0.8.2) terser (1.1.17) execjs (>= 0.3.0, < 3) @@ -276,6 +292,7 @@ GEM activemodel (>= 6.0.0) bindex (>= 0.4.0) railties (>= 6.0.0) + webrick (1.8.1) websocket-driver (0.7.6) websocket-extensions (>= 0.1.0) websocket-extensions (0.1.5) @@ -291,10 +308,10 @@ DEPENDENCIES devise (~> 4.9, >= 4.9.2) devise-encryptable (~> 0.2.0) dotenv-rails (~> 2.8, >= 2.8.1) - factory_girl_rails (~> 4.9) globalize (~> 6.2, >= 6.2.1) haml (~> 6.1, >= 6.1.1) http_accept_language (~> 2.1, >= 2.1.1) + httparty (~> 0.21.0) jsbundling-rails (~> 1.1) letter_opener (~> 1.8, >= 1.8.1) mysql2 (~> 0.5.5) @@ -302,13 +319,12 @@ DEPENDENCIES parallel (~> 1.23) puma (~> 6.3, >= 6.3.1) rack-attack (~> 6.7) - rails (= 7.0.7.1) + rails (~> 7.1, >= 7.1.1) rails-i18n (~> 7.0, >= 7.0.7) rdiscount (~> 2.2, >= 2.2.7.1) react-rails (~> 2.7, >= 2.7.1) record_tag_helper (~> 1.0, >= 1.0.1) rest-client (~> 2.1) - rspec-rails (~> 2.0.0.beta.22) sanitize (~> 6.0, >= 6.0.2) sass-rails (~> 6.0) sprockets (~> 4.2) diff --git a/README b/README deleted file mode 100644 index 71768ac8..00000000 --- a/README +++ /dev/null @@ -1,8 +0,0 @@ -An extension of Dress to Impress (PHP) that runs on Ruby on Rails. -I wanted to use Rails initially for Impress, but hoped that using -PHP would allow me to attract more developers. Looks like that -wasn't the case, so I just went with what I loved and made the -items database in Rails. - -Future Impress sections will likely find themselves in this -project, rather than the PHP project. diff --git a/README.md b/README.md new file mode 100644 index 00000000..63da4abc --- /dev/null +++ b/README.md @@ -0,0 +1,7 @@ +Dress to Impress beach logo + +# Dress to Impress + +Oh! We've been revitalizing the Rails app! Fun! + +There'll be more to say about it here soon :3 diff --git a/app/assets/javascripts/ZeroClipboard.min.js b/app/assets/javascripts/ZeroClipboard.min.js deleted file mode 100644 index 6ecd0885..00000000 --- a/app/assets/javascripts/ZeroClipboard.min.js +++ /dev/null @@ -1,10 +0,0 @@ -/*! - * ZeroClipboard - * The ZeroClipboard library provides an easy way to copy text to the clipboard using an invisible Adobe Flash movie and a JavaScript interface. - * Copyright (c) 2009-2014 Jon Rohan, James M. Greene - * Licensed MIT - * http://zeroclipboard.org/ - * v2.2.0 - */ -!function(a,b){"use strict";var c,d,e,f=a,g=f.document,h=f.navigator,i=f.setTimeout,j=f.clearTimeout,k=f.setInterval,l=f.clearInterval,m=f.getComputedStyle,n=f.encodeURIComponent,o=f.ActiveXObject,p=f.Error,q=f.Number.parseInt||f.parseInt,r=f.Number.parseFloat||f.parseFloat,s=f.Number.isNaN||f.isNaN,t=f.Date.now,u=f.Object.keys,v=f.Object.defineProperty,w=f.Object.prototype.hasOwnProperty,x=f.Array.prototype.slice,y=function(){var a=function(a){return a};if("function"==typeof f.wrap&&"function"==typeof f.unwrap)try{var b=g.createElement("div"),c=f.unwrap(b);1===b.nodeType&&c&&1===c.nodeType&&(a=f.unwrap)}catch(d){}return a}(),z=function(a){return x.call(a,0)},A=function(){var a,c,d,e,f,g,h=z(arguments),i=h[0]||{};for(a=1,c=h.length;c>a;a++)if(null!=(d=h[a]))for(e in d)w.call(d,e)&&(f=i[e],g=d[e],i!==g&&g!==b&&(i[e]=g));return i},B=function(a){var b,c,d,e;if("object"!=typeof a||null==a||"number"==typeof a.nodeType)b=a;else if("number"==typeof a.length)for(b=[],c=0,d=a.length;d>c;c++)w.call(a,c)&&(b[c]=B(a[c]));else{b={};for(e in a)w.call(a,e)&&(b[e]=B(a[e]))}return b},C=function(a,b){for(var c={},d=0,e=b.length;e>d;d++)b[d]in a&&(c[b[d]]=a[b[d]]);return c},D=function(a,b){var c={};for(var d in a)-1===b.indexOf(d)&&(c[d]=a[d]);return c},E=function(a){if(a)for(var b in a)w.call(a,b)&&delete a[b];return a},F=function(a,b){if(a&&1===a.nodeType&&a.ownerDocument&&b&&(1===b.nodeType&&b.ownerDocument&&b.ownerDocument===a.ownerDocument||9===b.nodeType&&!b.ownerDocument&&b===a.ownerDocument))do{if(a===b)return!0;a=a.parentNode}while(a);return!1},G=function(a){var b;return"string"==typeof a&&a&&(b=a.split("#")[0].split("?")[0],b=a.slice(0,a.lastIndexOf("/")+1)),b},H=function(a){var b,c;return"string"==typeof a&&a&&(c=a.match(/^(?:|[^:@]*@|.+\)@(?=http[s]?|file)|.+?\s+(?: at |@)(?:[^:\(]+ )*[\(]?)((?:http[s]?|file):\/\/[\/]?.+?\/[^:\)]*?)(?::\d+)(?::\d+)?/),c&&c[1]?b=c[1]:(c=a.match(/\)@((?:http[s]?|file):\/\/[\/]?.+?\/[^:\)]*?)(?::\d+)(?::\d+)?/),c&&c[1]&&(b=c[1]))),b},I=function(){var a,b;try{throw new p}catch(c){b=c}return b&&(a=b.sourceURL||b.fileName||H(b.stack)),a},J=function(){var a,c,d;if(g.currentScript&&(a=g.currentScript.src))return a;if(c=g.getElementsByTagName("script"),1===c.length)return c[0].src||b;if("readyState"in c[0])for(d=c.length;d--;)if("interactive"===c[d].readyState&&(a=c[d].src))return a;return"loading"===g.readyState&&(a=c[c.length-1].src)?a:(a=I())?a:b},K=function(){var a,c,d,e=g.getElementsByTagName("script");for(a=e.length;a--;){if(!(d=e[a].src)){c=null;break}if(d=G(d),null==c)c=d;else if(c!==d){c=null;break}}return c||b},L=function(){var a=G(J())||K()||"";return a+"ZeroClipboard.swf"},M=function(){return null==a.opener&&(!!a.top&&a!=a.top||!!a.parent&&a!=a.parent)}(),N={bridge:null,version:"0.0.0",pluginType:"unknown",disabled:null,outdated:null,sandboxed:null,unavailable:null,degraded:null,deactivated:null,overdue:null,ready:null},O="11.0.0",P={},Q={},R=null,S=0,T=0,U={ready:"Flash communication is established",error:{"flash-disabled":"Flash is disabled or not installed. May also be attempting to run Flash in a sandboxed iframe, which is impossible.","flash-outdated":"Flash is too outdated to support ZeroClipboard","flash-sandboxed":"Attempting to run Flash in a sandboxed iframe, which is impossible","flash-unavailable":"Flash is unable to communicate bidirectionally with JavaScript","flash-degraded":"Flash is unable to preserve data fidelity when communicating with JavaScript","flash-deactivated":"Flash is too outdated for your browser and/or is configured as click-to-activate.\nThis may also mean that the ZeroClipboard SWF object could not be loaded, so please check your `swfPath` configuration and/or network connectivity.\nMay also be attempting to run Flash in a sandboxed iframe, which is impossible.","flash-overdue":"Flash communication was established but NOT within the acceptable time limit","version-mismatch":"ZeroClipboard JS version number does not match ZeroClipboard SWF version number","clipboard-error":"At least one error was thrown while ZeroClipboard was attempting to inject your data into the clipboard","config-mismatch":"ZeroClipboard configuration does not match Flash's reality","swf-not-found":"The ZeroClipboard SWF object could not be loaded, so please check your `swfPath` configuration and/or network connectivity"}},V=["flash-unavailable","flash-degraded","flash-overdue","version-mismatch","config-mismatch","clipboard-error"],W=["flash-disabled","flash-outdated","flash-sandboxed","flash-unavailable","flash-degraded","flash-deactivated","flash-overdue"],X=new RegExp("^flash-("+W.map(function(a){return a.replace(/^flash-/,"")}).join("|")+")$"),Y=new RegExp("^flash-("+W.slice(1).map(function(a){return a.replace(/^flash-/,"")}).join("|")+")$"),Z={swfPath:L(),trustedDomains:a.location.host?[a.location.host]:[],cacheBust:!0,forceEnhancedClipboard:!1,flashLoadTimeout:3e4,autoActivate:!0,bubbleEvents:!0,containerId:"global-zeroclipboard-html-bridge",containerClass:"global-zeroclipboard-container",swfObjectId:"global-zeroclipboard-flash-bridge",hoverClass:"zeroclipboard-is-hover",activeClass:"zeroclipboard-is-active",forceHandCursor:!1,title:null,zIndex:999999999},$=function(a){if("object"==typeof a&&null!==a)for(var b in a)if(w.call(a,b))if(/^(?:forceHandCursor|title|zIndex|bubbleEvents)$/.test(b))Z[b]=a[b];else if(null==N.bridge)if("containerId"===b||"swfObjectId"===b){if(!nb(a[b]))throw new Error("The specified `"+b+"` value is not valid as an HTML4 Element ID");Z[b]=a[b]}else Z[b]=a[b];{if("string"!=typeof a||!a)return B(Z);if(w.call(Z,a))return Z[a]}},_=function(){return Tb(),{browser:C(h,["userAgent","platform","appName"]),flash:D(N,["bridge"]),zeroclipboard:{version:Vb.version,config:Vb.config()}}},ab=function(){return!!(N.disabled||N.outdated||N.sandboxed||N.unavailable||N.degraded||N.deactivated)},bb=function(a,d){var e,f,g,h={};if("string"==typeof a&&a)g=a.toLowerCase().split(/\s+/);else if("object"==typeof a&&a&&"undefined"==typeof d)for(e in a)w.call(a,e)&&"string"==typeof e&&e&&"function"==typeof a[e]&&Vb.on(e,a[e]);if(g&&g.length){for(e=0,f=g.length;f>e;e++)a=g[e].replace(/^on/,""),h[a]=!0,P[a]||(P[a]=[]),P[a].push(d);if(h.ready&&N.ready&&Vb.emit({type:"ready"}),h.error){for(e=0,f=W.length;f>e;e++)if(N[W[e].replace(/^flash-/,"")]===!0){Vb.emit({type:"error",name:W[e]});break}c!==b&&Vb.version!==c&&Vb.emit({type:"error",name:"version-mismatch",jsVersion:Vb.version,swfVersion:c})}}return Vb},cb=function(a,b){var c,d,e,f,g;if(0===arguments.length)f=u(P);else if("string"==typeof a&&a)f=a.split(/\s+/);else if("object"==typeof a&&a&&"undefined"==typeof b)for(c in a)w.call(a,c)&&"string"==typeof c&&c&&"function"==typeof a[c]&&Vb.off(c,a[c]);if(f&&f.length)for(c=0,d=f.length;d>c;c++)if(a=f[c].toLowerCase().replace(/^on/,""),g=P[a],g&&g.length)if(b)for(e=g.indexOf(b);-1!==e;)g.splice(e,1),e=g.indexOf(b,e);else g.length=0;return Vb},db=function(a){var b;return b="string"==typeof a&&a?B(P[a])||null:B(P)},eb=function(a){var b,c,d;return a=ob(a),a&&!vb(a)?"ready"===a.type&&N.overdue===!0?Vb.emit({type:"error",name:"flash-overdue"}):(b=A({},a),tb.call(this,b),"copy"===a.type&&(d=Db(Q),c=d.data,R=d.formatMap),c):void 0},fb=function(){var a=N.sandboxed;if(Tb(),"boolean"!=typeof N.ready&&(N.ready=!1),N.sandboxed!==a&&N.sandboxed===!0)N.ready=!1,Vb.emit({type:"error",name:"flash-sandboxed"});else if(!Vb.isFlashUnusable()&&null===N.bridge){var b=Z.flashLoadTimeout;"number"==typeof b&&b>=0&&(S=i(function(){"boolean"!=typeof N.deactivated&&(N.deactivated=!0),N.deactivated===!0&&Vb.emit({type:"error",name:"flash-deactivated"})},b)),N.overdue=!1,Bb()}},gb=function(){Vb.clearData(),Vb.blur(),Vb.emit("destroy"),Cb(),Vb.off()},hb=function(a,b){var c;if("object"==typeof a&&a&&"undefined"==typeof b)c=a,Vb.clearData();else{if("string"!=typeof a||!a)return;c={},c[a]=b}for(var d in c)"string"==typeof d&&d&&w.call(c,d)&&"string"==typeof c[d]&&c[d]&&(Q[d]=c[d])},ib=function(a){"undefined"==typeof a?(E(Q),R=null):"string"==typeof a&&w.call(Q,a)&&delete Q[a]},jb=function(a){return"undefined"==typeof a?B(Q):"string"==typeof a&&w.call(Q,a)?Q[a]:void 0},kb=function(a){if(a&&1===a.nodeType){d&&(Lb(d,Z.activeClass),d!==a&&Lb(d,Z.hoverClass)),d=a,Kb(a,Z.hoverClass);var b=a.getAttribute("title")||Z.title;if("string"==typeof b&&b){var c=Ab(N.bridge);c&&c.setAttribute("title",b)}var e=Z.forceHandCursor===!0||"pointer"===Mb(a,"cursor");Rb(e),Qb()}},lb=function(){var a=Ab(N.bridge);a&&(a.removeAttribute("title"),a.style.left="0px",a.style.top="-9999px",a.style.width="1px",a.style.height="1px"),d&&(Lb(d,Z.hoverClass),Lb(d,Z.activeClass),d=null)},mb=function(){return d||null},nb=function(a){return"string"==typeof a&&a&&/^[A-Za-z][A-Za-z0-9_:\-\.]*$/.test(a)},ob=function(a){var b;if("string"==typeof a&&a?(b=a,a={}):"object"==typeof a&&a&&"string"==typeof a.type&&a.type&&(b=a.type),b){b=b.toLowerCase(),!a.target&&(/^(copy|aftercopy|_click)$/.test(b)||"error"===b&&"clipboard-error"===a.name)&&(a.target=e),A(a,{type:b,target:a.target||d||null,relatedTarget:a.relatedTarget||null,currentTarget:N&&N.bridge||null,timeStamp:a.timeStamp||t()||null});var c=U[a.type];return"error"===a.type&&a.name&&c&&(c=c[a.name]),c&&(a.message=c),"ready"===a.type&&A(a,{target:null,version:N.version}),"error"===a.type&&(X.test(a.name)&&A(a,{target:null,minimumVersion:O}),Y.test(a.name)&&A(a,{version:N.version})),"copy"===a.type&&(a.clipboardData={setData:Vb.setData,clearData:Vb.clearData}),"aftercopy"===a.type&&(a=Eb(a,R)),a.target&&!a.relatedTarget&&(a.relatedTarget=pb(a.target)),qb(a)}},pb=function(a){var b=a&&a.getAttribute&&a.getAttribute("data-clipboard-target");return b?g.getElementById(b):null},qb=function(a){if(a&&/^_(?:click|mouse(?:over|out|down|up|move))$/.test(a.type)){var c=a.target,d="_mouseover"===a.type&&a.relatedTarget?a.relatedTarget:b,e="_mouseout"===a.type&&a.relatedTarget?a.relatedTarget:b,h=Nb(c),i=f.screenLeft||f.screenX||0,j=f.screenTop||f.screenY||0,k=g.body.scrollLeft+g.documentElement.scrollLeft,l=g.body.scrollTop+g.documentElement.scrollTop,m=h.left+("number"==typeof a._stageX?a._stageX:0),n=h.top+("number"==typeof a._stageY?a._stageY:0),o=m-k,p=n-l,q=i+o,r=j+p,s="number"==typeof a.movementX?a.movementX:0,t="number"==typeof a.movementY?a.movementY:0;delete a._stageX,delete a._stageY,A(a,{srcElement:c,fromElement:d,toElement:e,screenX:q,screenY:r,pageX:m,pageY:n,clientX:o,clientY:p,x:o,y:p,movementX:s,movementY:t,offsetX:0,offsetY:0,layerX:0,layerY:0})}return a},rb=function(a){var b=a&&"string"==typeof a.type&&a.type||"";return!/^(?:(?:before)?copy|destroy)$/.test(b)},sb=function(a,b,c,d){d?i(function(){a.apply(b,c)},0):a.apply(b,c)},tb=function(a){if("object"==typeof a&&a&&a.type){var b=rb(a),c=P["*"]||[],d=P[a.type]||[],e=c.concat(d);if(e&&e.length){var g,h,i,j,k,l=this;for(g=0,h=e.length;h>g;g++)i=e[g],j=l,"string"==typeof i&&"function"==typeof f[i]&&(i=f[i]),"object"==typeof i&&i&&"function"==typeof i.handleEvent&&(j=i,i=i.handleEvent),"function"==typeof i&&(k=A({},a),sb(i,j,[k],b))}return this}},ub=function(a){var b=null;return(M===!1||a&&"error"===a.type&&a.name&&-1!==V.indexOf(a.name))&&(b=!1),b},vb=function(a){var b=a.target||d||null,f="swf"===a._source;switch(delete a._source,a.type){case"error":var g="flash-sandboxed"===a.name||ub(a);"boolean"==typeof g&&(N.sandboxed=g),-1!==W.indexOf(a.name)?A(N,{disabled:"flash-disabled"===a.name,outdated:"flash-outdated"===a.name,unavailable:"flash-unavailable"===a.name,degraded:"flash-degraded"===a.name,deactivated:"flash-deactivated"===a.name,overdue:"flash-overdue"===a.name,ready:!1}):"version-mismatch"===a.name&&(c=a.swfVersion,A(N,{disabled:!1,outdated:!1,unavailable:!1,degraded:!1,deactivated:!1,overdue:!1,ready:!1})),Pb();break;case"ready":c=a.swfVersion;var h=N.deactivated===!0;A(N,{disabled:!1,outdated:!1,sandboxed:!1,unavailable:!1,degraded:!1,deactivated:!1,overdue:h,ready:!h}),Pb();break;case"beforecopy":e=b;break;case"copy":var i,j,k=a.relatedTarget;!Q["text/html"]&&!Q["text/plain"]&&k&&(j=k.value||k.outerHTML||k.innerHTML)&&(i=k.value||k.textContent||k.innerText)?(a.clipboardData.clearData(),a.clipboardData.setData("text/plain",i),j!==i&&a.clipboardData.setData("text/html",j)):!Q["text/plain"]&&a.target&&(i=a.target.getAttribute("data-clipboard-text"))&&(a.clipboardData.clearData(),a.clipboardData.setData("text/plain",i));break;case"aftercopy":wb(a),Vb.clearData(),b&&b!==Jb()&&b.focus&&b.focus();break;case"_mouseover":Vb.focus(b),Z.bubbleEvents===!0&&f&&(b&&b!==a.relatedTarget&&!F(a.relatedTarget,b)&&xb(A({},a,{type:"mouseenter",bubbles:!1,cancelable:!1})),xb(A({},a,{type:"mouseover"})));break;case"_mouseout":Vb.blur(),Z.bubbleEvents===!0&&f&&(b&&b!==a.relatedTarget&&!F(a.relatedTarget,b)&&xb(A({},a,{type:"mouseleave",bubbles:!1,cancelable:!1})),xb(A({},a,{type:"mouseout"})));break;case"_mousedown":Kb(b,Z.activeClass),Z.bubbleEvents===!0&&f&&xb(A({},a,{type:a.type.slice(1)}));break;case"_mouseup":Lb(b,Z.activeClass),Z.bubbleEvents===!0&&f&&xb(A({},a,{type:a.type.slice(1)}));break;case"_click":e=null,Z.bubbleEvents===!0&&f&&xb(A({},a,{type:a.type.slice(1)}));break;case"_mousemove":Z.bubbleEvents===!0&&f&&xb(A({},a,{type:a.type.slice(1)}))}return/^_(?:click|mouse(?:over|out|down|up|move))$/.test(a.type)?!0:void 0},wb=function(a){if(a.errors&&a.errors.length>0){var b=B(a);A(b,{type:"error",name:"clipboard-error"}),delete b.success,i(function(){Vb.emit(b)},0)}},xb=function(a){if(a&&"string"==typeof a.type&&a){var b,c=a.target||null,d=c&&c.ownerDocument||g,e={view:d.defaultView||f,canBubble:!0,cancelable:!0,detail:"click"===a.type?1:0,button:"number"==typeof a.which?a.which-1:"number"==typeof a.button?a.button:d.createEvent?0:1},h=A(e,a);c&&d.createEvent&&c.dispatchEvent&&(h=[h.type,h.canBubble,h.cancelable,h.view,h.detail,h.screenX,h.screenY,h.clientX,h.clientY,h.ctrlKey,h.altKey,h.shiftKey,h.metaKey,h.button,h.relatedTarget],b=d.createEvent("MouseEvents"),b.initMouseEvent&&(b.initMouseEvent.apply(b,h),b._source="js",c.dispatchEvent(b)))}},yb=function(){var a=Z.flashLoadTimeout;if("number"==typeof a&&a>=0){var b=Math.min(1e3,a/10),c=Z.swfObjectId+"_fallbackContent";T=k(function(){var a=g.getElementById(c);Ob(a)&&(Pb(),N.deactivated=null,Vb.emit({type:"error",name:"swf-not-found"}))},b)}},zb=function(){var a=g.createElement("div");return a.id=Z.containerId,a.className=Z.containerClass,a.style.position="absolute",a.style.left="0px",a.style.top="-9999px",a.style.width="1px",a.style.height="1px",a.style.zIndex=""+Sb(Z.zIndex),a},Ab=function(a){for(var b=a&&a.parentNode;b&&"OBJECT"===b.nodeName&&b.parentNode;)b=b.parentNode;return b||null},Bb=function(){var a,b=N.bridge,c=Ab(b);if(!b){var d=Ib(f.location.host,Z),e="never"===d?"none":"all",h=Gb(A({jsVersion:Vb.version},Z)),i=Z.swfPath+Fb(Z.swfPath,Z);c=zb();var j=g.createElement("div");c.appendChild(j),g.body.appendChild(c);var k=g.createElement("div"),l="activex"===N.pluginType;k.innerHTML='"+(l?'':"")+'
 
',b=k.firstChild,k=null,y(b).ZeroClipboard=Vb,c.replaceChild(b,j),yb()}return b||(b=g[Z.swfObjectId],b&&(a=b.length)&&(b=b[a-1]),!b&&c&&(b=c.firstChild)),N.bridge=b||null,b},Cb=function(){var a=N.bridge;if(a){var d=Ab(a);d&&("activex"===N.pluginType&&"readyState"in a?(a.style.display="none",function e(){if(4===a.readyState){for(var b in a)"function"==typeof a[b]&&(a[b]=null);a.parentNode&&a.parentNode.removeChild(a),d.parentNode&&d.parentNode.removeChild(d)}else i(e,10)}()):(a.parentNode&&a.parentNode.removeChild(a),d.parentNode&&d.parentNode.removeChild(d))),Pb(),N.ready=null,N.bridge=null,N.deactivated=null,c=b}},Db=function(a){var b={},c={};if("object"==typeof a&&a){for(var d in a)if(d&&w.call(a,d)&&"string"==typeof a[d]&&a[d])switch(d.toLowerCase()){case"text/plain":case"text":case"air:text":case"flash:text":b.text=a[d],c.text=d;break;case"text/html":case"html":case"air:html":case"flash:html":b.html=a[d],c.html=d;break;case"application/rtf":case"text/rtf":case"rtf":case"richtext":case"air:rtf":case"flash:rtf":b.rtf=a[d],c.rtf=d}return{data:b,formatMap:c}}},Eb=function(a,b){if("object"!=typeof a||!a||"object"!=typeof b||!b)return a;var c={};for(var d in a)if(w.call(a,d))if("errors"===d){c[d]=a[d]?a[d].slice():[];for(var e=0,f=c[d].length;f>e;e++)c[d][e].format=b[c[d][e].format]}else if("success"!==d&&"data"!==d)c[d]=a[d];else{c[d]={};var g=a[d];for(var h in g)h&&w.call(g,h)&&w.call(b,h)&&(c[d][b[h]]=g[h])}return c},Fb=function(a,b){var c=null==b||b&&b.cacheBust===!0;return c?(-1===a.indexOf("?")?"?":"&")+"noCache="+t():""},Gb=function(a){var b,c,d,e,g="",h=[];if(a.trustedDomains&&("string"==typeof a.trustedDomains?e=[a.trustedDomains]:"object"==typeof a.trustedDomains&&"length"in a.trustedDomains&&(e=a.trustedDomains)),e&&e.length)for(b=0,c=e.length;c>b;b++)if(w.call(e,b)&&e[b]&&"string"==typeof e[b]){if(d=Hb(e[b]),!d)continue;if("*"===d){h.length=0,h.push(d);break}h.push.apply(h,[d,"//"+d,f.location.protocol+"//"+d])}return h.length&&(g+="trustedOrigins="+n(h.join(","))),a.forceEnhancedClipboard===!0&&(g+=(g?"&":"")+"forceEnhancedClipboard=true"),"string"==typeof a.swfObjectId&&a.swfObjectId&&(g+=(g?"&":"")+"swfObjectId="+n(a.swfObjectId)),"string"==typeof a.jsVersion&&a.jsVersion&&(g+=(g?"&":"")+"jsVersion="+n(a.jsVersion)),g},Hb=function(a){if(null==a||""===a)return null;if(a=a.replace(/^\s+|\s+$/g,""),""===a)return null;var b=a.indexOf("//");a=-1===b?a:a.slice(b+2);var c=a.indexOf("/");return a=-1===c?a:-1===b||0===c?null:a.slice(0,c),a&&".swf"===a.slice(-4).toLowerCase()?null:a||null},Ib=function(){var a=function(a){var b,c,d,e=[];if("string"==typeof a&&(a=[a]),"object"!=typeof a||!a||"number"!=typeof a.length)return e;for(b=0,c=a.length;c>b;b++)if(w.call(a,b)&&(d=Hb(a[b]))){if("*"===d){e.length=0,e.push("*");break}-1===e.indexOf(d)&&e.push(d)}return e};return function(b,c){var d=Hb(c.swfPath);null===d&&(d=b);var e=a(c.trustedDomains),f=e.length;if(f>0){if(1===f&&"*"===e[0])return"always";if(-1!==e.indexOf(b))return 1===f&&b===d?"sameDomain":"always"}return"never"}}(),Jb=function(){try{return g.activeElement}catch(a){return null}},Kb=function(a,b){var c,d,e,f=[];if("string"==typeof b&&b&&(f=b.split(/\s+/)),a&&1===a.nodeType&&f.length>0)if(a.classList)for(c=0,d=f.length;d>c;c++)a.classList.add(f[c]);else if(a.hasOwnProperty("className")){for(e=" "+a.className+" ",c=0,d=f.length;d>c;c++)-1===e.indexOf(" "+f[c]+" ")&&(e+=f[c]+" ");a.className=e.replace(/^\s+|\s+$/g,"")}return a},Lb=function(a,b){var c,d,e,f=[];if("string"==typeof b&&b&&(f=b.split(/\s+/)),a&&1===a.nodeType&&f.length>0)if(a.classList&&a.classList.length>0)for(c=0,d=f.length;d>c;c++)a.classList.remove(f[c]);else if(a.className){for(e=(" "+a.className+" ").replace(/[\r\n\t]/g," "),c=0,d=f.length;d>c;c++)e=e.replace(" "+f[c]+" "," ");a.className=e.replace(/^\s+|\s+$/g,"")}return a},Mb=function(a,b){var c=m(a,null).getPropertyValue(b);return"cursor"!==b||c&&"auto"!==c||"A"!==a.nodeName?c:"pointer"},Nb=function(a){var b={left:0,top:0,width:0,height:0};if(a.getBoundingClientRect){var c=a.getBoundingClientRect(),d=f.pageXOffset,e=f.pageYOffset,h=g.documentElement.clientLeft||0,i=g.documentElement.clientTop||0,j=0,k=0;if("relative"===Mb(g.body,"position")){var l=g.body.getBoundingClientRect(),m=g.documentElement.getBoundingClientRect();j=l.left-m.left||0,k=l.top-m.top||0}b.left=c.left+d-h-j,b.top=c.top+e-i-k,b.width="width"in c?c.width:c.right-c.left,b.height="height"in c?c.height:c.bottom-c.top}return b},Ob=function(a){if(!a)return!1;var b=m(a,null),c=r(b.height)>0,d=r(b.width)>0,e=r(b.top)>=0,f=r(b.left)>=0,g=c&&d&&e&&f,h=g?null:Nb(a),i="none"!==b.display&&"collapse"!==b.visibility&&(g||!!h&&(c||h.height>0)&&(d||h.width>0)&&(e||h.top>=0)&&(f||h.left>=0));return i},Pb=function(){j(S),S=0,l(T),T=0},Qb=function(){var a;if(d&&(a=Ab(N.bridge))){var b=Nb(d);A(a.style,{width:b.width+"px",height:b.height+"px",top:b.top+"px",left:b.left+"px",zIndex:""+Sb(Z.zIndex)})}},Rb=function(a){N.ready===!0&&(N.bridge&&"function"==typeof N.bridge.setHandCursor?N.bridge.setHandCursor(a):N.ready=!1)},Sb=function(a){if(/^(?:auto|inherit)$/.test(a))return a;var b;return"number"!=typeof a||s(a)?"string"==typeof a&&(b=Sb(q(a,10))):b=a,"number"==typeof b?b:"auto"},Tb=function(b){var c,d,e,f=N.sandboxed,g=null;if(b=b===!0,M===!1)g=!1;else{try{d=a.frameElement||null}catch(h){e={name:h.name,message:h.message}}if(d&&1===d.nodeType&&"IFRAME"===d.nodeName)try{g=d.hasAttribute("sandbox")}catch(h){g=null}else{try{c=document.domain||null}catch(h){c=null}(null===c||e&&"SecurityError"===e.name&&/(^|[\s\(\[@])sandbox(es|ed|ing|[\s\.,!\)\]@]|$)/.test(e.message.toLowerCase()))&&(g=!0)}}return N.sandboxed=g,f===g||b||Ub(o),g},Ub=function(a){function b(a){var b=a.match(/[\d]+/g);return b.length=3,b.join(".")}function c(a){return!!a&&(a=a.toLowerCase())&&(/^(pepflashplayer\.dll|libpepflashplayer\.so|pepperflashplayer\.plugin)$/.test(a)||"chrome.plugin"===a.slice(-13))}function d(a){a&&(i=!0,a.version&&(l=b(a.version)),!l&&a.description&&(l=b(a.description)),a.filename&&(k=c(a.filename)))}var e,f,g,i=!1,j=!1,k=!1,l="";if(h.plugins&&h.plugins.length)e=h.plugins["Shockwave Flash"],d(e),h.plugins["Shockwave Flash 2.0"]&&(i=!0,l="2.0.0.11");else if(h.mimeTypes&&h.mimeTypes.length)g=h.mimeTypes["application/x-shockwave-flash"],e=g&&g.enabledPlugin,d(e);else if("undefined"!=typeof a){j=!0;try{f=new a("ShockwaveFlash.ShockwaveFlash.7"),i=!0,l=b(f.GetVariable("$version"))}catch(m){try{f=new a("ShockwaveFlash.ShockwaveFlash.6"),i=!0,l="6.0.21"}catch(n){try{f=new a("ShockwaveFlash.ShockwaveFlash"),i=!0,l=b(f.GetVariable("$version"))}catch(o){j=!1}}}}N.disabled=i!==!0,N.outdated=l&&r(l)e;e++)a=g[e].replace(/^on/,""),h[a]=!0,j[a]||(j[a]=[]),j[a].push(d);if(h.ready&&N.ready&&this.emit({type:"ready",client:this}),h.error){for(e=0,f=W.length;f>e;e++)if(N[W[e].replace(/^flash-/,"")]){this.emit({type:"error",name:W[e],client:this});break}c!==b&&Vb.version!==c&&this.emit({type:"error",name:"version-mismatch",jsVersion:Vb.version,swfVersion:c})}}return this},bc=function(a,b){var c,d,e,f,g,h=Xb[this.id],i=h&&h.handlers;if(!i)return this;if(0===arguments.length)f=u(i);else if("string"==typeof a&&a)f=a.split(/\s+/);else if("object"==typeof a&&a&&"undefined"==typeof b)for(c in a)w.call(a,c)&&"string"==typeof c&&c&&"function"==typeof a[c]&&this.off(c,a[c]);if(f&&f.length)for(c=0,d=f.length;d>c;c++)if(a=f[c].toLowerCase().replace(/^on/,""),g=i[a],g&&g.length)if(b)for(e=g.indexOf(b);-1!==e;)g.splice(e,1),e=g.indexOf(b,e);else g.length=0;return this},cc=function(a){var b=null,c=Xb[this.id]&&Xb[this.id].handlers;return c&&(b="string"==typeof a&&a?c[a]?c[a].slice(0):[]:B(c)),b},dc=function(a){if(ic.call(this,a)){"object"==typeof a&&a&&"string"==typeof a.type&&a.type&&(a=A({},a));var b=A({},ob(a),{client:this});jc.call(this,b)}return this},ec=function(a){if(!Xb[this.id])throw new Error("Attempted to clip element(s) to a destroyed ZeroClipboard client instance");a=kc(a);for(var b=0;b0,e=!a.target||d&&-1!==c.indexOf(a.target),f=a.relatedTarget&&d&&-1!==c.indexOf(a.relatedTarget),g=a.client&&a.client===this;return b&&(e||f||g)?!0:!1},jc=function(a){var b=Xb[this.id];if("object"==typeof a&&a&&a.type&&b){var c=rb(a),d=b&&b.handlers["*"]||[],e=b&&b.handlers[a.type]||[],g=d.concat(e);if(g&&g.length){var h,i,j,k,l,m=this;for(h=0,i=g.length;i>h;h++)j=g[h],k=m,"string"==typeof j&&"function"==typeof f[j]&&(j=f[j]),"object"==typeof j&&j&&"function"==typeof j.handleEvent&&(k=j,j=j.handleEvent),"function"==typeof j&&(l=A({},a),sb(j,k,[l],c))}}},kc=function(a){return"string"==typeof a&&(a=[]),"number"!=typeof a.length?[a]:a},lc=function(a){if(a&&1===a.nodeType){var b=function(a){(a||(a=f.event))&&("js"!==a._source&&(a.stopImmediatePropagation(),a.preventDefault()),delete a._source)},c=function(c){(c||(c=f.event))&&(b(c),Vb.focus(a))};a.addEventListener("mouseover",c,!1),a.addEventListener("mouseout",b,!1),a.addEventListener("mouseenter",b,!1),a.addEventListener("mouseleave",b,!1),a.addEventListener("mousemove",b,!1),$b[a.zcClippingId]={mouseover:c,mouseout:b,mouseenter:b,mouseleave:b,mousemove:b}}},mc=function(a){if(a&&1===a.nodeType){var b=$b[a.zcClippingId];if("object"==typeof b&&b){for(var c,d,e=["move","leave","enter","out","over"],f=0,g=e.length;g>f;f++)c="mouse"+e[f],d=b[c],"function"==typeof d&&a.removeEventListener(c,d,!1);delete $b[a.zcClippingId]}}};Vb._createClient=function(){_b.apply(this,z(arguments))},Vb.prototype.on=function(){return ac.apply(this,z(arguments))},Vb.prototype.off=function(){return bc.apply(this,z(arguments))},Vb.prototype.handlers=function(){return cc.apply(this,z(arguments))},Vb.prototype.emit=function(){return dc.apply(this,z(arguments))},Vb.prototype.clip=function(){return ec.apply(this,z(arguments))},Vb.prototype.unclip=function(){return fc.apply(this,z(arguments))},Vb.prototype.elements=function(){return gc.apply(this,z(arguments))},Vb.prototype.destroy=function(){return hc.apply(this,z(arguments))},Vb.prototype.setText=function(a){if(!Xb[this.id])throw new Error("Attempted to set pending clipboard data from a destroyed ZeroClipboard client instance");return Vb.setData("text/plain",a),this},Vb.prototype.setHtml=function(a){if(!Xb[this.id])throw new Error("Attempted to set pending clipboard data from a destroyed ZeroClipboard client instance");return Vb.setData("text/html",a),this},Vb.prototype.setRichText=function(a){if(!Xb[this.id])throw new Error("Attempted to set pending clipboard data from a destroyed ZeroClipboard client instance");return Vb.setData("application/rtf",a),this},Vb.prototype.setData=function(){if(!Xb[this.id])throw new Error("Attempted to set pending clipboard data from a destroyed ZeroClipboard client instance");return Vb.setData.apply(this,z(arguments)),this},Vb.prototype.clearData=function(){if(!Xb[this.id])throw new Error("Attempted to clear pending clipboard data from a destroyed ZeroClipboard client instance");return Vb.clearData.apply(this,z(arguments)),this},Vb.prototype.getData=function(){if(!Xb[this.id])throw new Error("Attempted to get pending clipboard data from a destroyed ZeroClipboard client instance");return Vb.getData.apply(this,z(arguments))},"function"==typeof define&&define.amd?define(function(){return Vb}):"object"==typeof module&&module&&"object"==typeof module.exports&&module.exports?module.exports=Vb:a.ZeroClipboard=Vb}(function(){return this||window}()); -//# sourceMappingURL=ZeroClipboard.min.map \ No newline at end of file diff --git a/app/assets/javascripts/ZeroClipboard.swf b/app/assets/javascripts/ZeroClipboard.swf deleted file mode 100644 index 8bad6a3e..00000000 Binary files a/app/assets/javascripts/ZeroClipboard.swf and /dev/null differ diff --git a/app/assets/javascripts/modeling.js.jsx b/app/assets/javascripts/modeling.js.jsx index 78582d31..c6634373 100644 --- a/app/assets/javascripts/modeling.js.jsx +++ b/app/assets/javascripts/modeling.js.jsx @@ -344,7 +344,7 @@ var Neopia = (function ($, I18n) { } var itemName = this.props.item.name; var imageSrc = - "http://pets.neopets.com/cpn/" + + "https://pets.neopets.com/cpn/" + petName + "/1/1.png?" + this.appearanceQuery(); diff --git a/app/assets/javascripts/outfits/new.js b/app/assets/javascripts/outfits/new.js index bec8b8ed..dd9d2cdf 100644 --- a/app/assets/javascripts/outfits/new.js +++ b/app/assets/javascripts/outfits/new.js @@ -48,7 +48,7 @@ function loadNotable() { // TODO: add HTTPS to notables - // $.getJSON('http://notables.openneo.net/api/1/days/ago/1?callback=?', function (response) { + // $.getJSON('https://notables.openneo.net/api/1/days/ago/1?callback=?', function (response) { // var notables = response.notables; // var i = Math.floor(Math.random() * notables.length); // Preview.Job.fallback = new Preview.Job.Name(notables[i].petName); @@ -87,7 +87,7 @@ // lol lazy code for prank image :P // TODO: HTTPS? return ( - "http://swfimages.impress.openneo.net" + + "https://swfimages.impress.openneo.net" + "/biology/000/000/0-2/" + key.substr(2) + "/300x300.png" diff --git a/app/assets/javascripts/pet_query.js b/app/assets/javascripts/pet_query.js index a217b6fd..15eea679 100644 --- a/app/assets/javascripts/pet_query.js +++ b/app/assets/javascripts/pet_query.js @@ -1,5 +1,5 @@ function petImage(id, size) { - return 'http://pets.neopets.com/' + id + '/1/' + size + '.png'; + return 'https://pets.neopets.com/' + id + '/1/' + size + '.png'; } var PetQuery = {}, diff --git a/app/assets/javascripts/pets/bulk.js b/app/assets/javascripts/pets/bulk.js index 47b83ebf..a86b9e7f 100644 --- a/app/assets/javascripts/pets/bulk.js +++ b/app/assets/javascripts/pets/bulk.js @@ -63,7 +63,7 @@ var DEBUG = (document.location.search.substr(0, 6) == '?debug'); } function petThumbnailUrl(pet_name) { - return 'http://pets.neopets.com/cpn/' + pet_name + '/1/1.png'; + return 'https://pets.neopets.com/cpn/' + pet_name + '/1/1.png'; } /* Items */ diff --git a/app/assets/stylesheets/campaigns/_show.sass b/app/assets/stylesheets/campaigns/_show.sass index e1066d01..5313c3db 100644 --- a/app/assets/stylesheets/campaigns/_show.sass +++ b/app/assets/stylesheets/campaigns/_show.sass @@ -191,7 +191,7 @@ body.campaigns-show, body.campaigns-current width: $outfit-inner-width &.banner - background-image: url(http://images.neopets.com/themes/004_bir_a2e60/footer_bg.png) + background-image: url(https://images.neopets.com/themes/004_bir_a2e60/footer_bg.png) background-position: 0 -60px border: 2px solid #006 color: white diff --git a/app/controllers/application_controller.rb b/app/controllers/application_controller.rb index 8684346d..92e0a417 100644 --- a/app/controllers/application_controller.rb +++ b/app/controllers/application_controller.rb @@ -41,11 +41,6 @@ class ApplicationController < ActionController::Base I18n.default_locale end - def localized_fragment_exist?(key) - localized_key = localize_fragment_key(key, locale) - fragment_exist?(localized_key) - end - def not_found(record_name='record') raise ActionController::RoutingError.new("#{record_name} not found") end diff --git a/app/controllers/sweeper_controller.rb b/app/controllers/sweeper_controller.rb deleted file mode 100644 index 42e9a157..00000000 --- a/app/controllers/sweeper_controller.rb +++ /dev/null @@ -1,8 +0,0 @@ -class SweeperController < ActionController::Base - def expire_action_proxy(options) - options[:only_path] = true - path = Rails.application.routes.url_helpers.url_for(options) - fragment_name = "#{LocalImpressHost}#{path}" - expire_fragment(fragment_name) - end -end diff --git a/app/helpers/application_helper.rb b/app/helpers/application_helper.rb index e5d6fc76..4b702b72 100644 --- a/app/helpers/application_helper.rb +++ b/app/helpers/application_helper.rb @@ -92,13 +92,9 @@ module ApplicationHelper end JAVASCRIPT_LIBRARIES = { - :addthis => '//s7.addthis.com/js/250/addthis_widget.js#username=openneo', - :bitly => '//bit.ly/javascript-api.js?version=latest&login=openneo&apiKey=R_4d0438829b7a99860de1d3edf55d8dc8', - :html5 => '//html5shim.googlecode.com/svn/trunk/html5.js', - :jquery => '//ajax.googleapis.com/ajax/libs/jquery/1.4.3/jquery.min.js', - :jquery20 => '//ajax.googleapis.com/ajax/libs/jquery/2.0.3/jquery.min.js', - :jquery_tmpl => '//ajax.microsoft.com/ajax/jquery.templates/beta1/jquery.tmpl.min.js', - :swfobject => '//ajax.googleapis.com/ajax/libs/swfobject/2.2/swfobject.js' + :jquery => 'https://ajax.googleapis.com/ajax/libs/jquery/1.4.3/jquery.min.js', + :jquery20 => 'https://ajax.googleapis.com/ajax/libs/jquery/2.0.3/jquery.min.js', + :jquery_tmpl => 'https://ajax.microsoft.com/ajax/jquery.templates/beta1/jquery.tmpl.min.js', } def include_javascript_libraries(*library_names) diff --git a/app/helpers/closet_hangers_helper.rb b/app/helpers/closet_hangers_helper.rb index 263bd44b..110dda93 100644 --- a/app/helpers/closet_hangers_helper.rb +++ b/app/helpers/closet_hangers_helper.rb @@ -13,11 +13,11 @@ module ClosetHangersHelper end def send_neomail_url(neopets_username) - "http://www.neopets.com/neomessages.phtml?type=send&recipient=#{CGI.escape neopets_username}" + "https://www.neopets.com/neomessages.phtml?type=send&recipient=#{CGI.escape neopets_username}" end def neopets_lookup_url(neopets_username) - "http://www.neopets.com/userlookup.phtml?user=#{CGI.escape neopets_username}" + "https://www.neopets.com/userlookup.phtml?user=#{CGI.escape neopets_username}" end def hangers_group_visibility_field_name(owned) @@ -75,7 +75,7 @@ module ClosetHangersHelper end def nc_icon_url - "http://#{request.host}#{image_path 'nc.png'}" + "https://#{request.host}#{image_path 'nc.png'}" end def petpage_closet_list_checked(closet_list, owned) diff --git a/app/helpers/closet_pages_helper.rb b/app/helpers/closet_pages_helper.rb index 1ed8454c..209ba29b 100644 --- a/app/helpers/closet_pages_helper.rb +++ b/app/helpers/closet_pages_helper.rb @@ -4,7 +4,7 @@ module ClosetPagesHelper end def neopets_login_url - "http://www.neopets.com/loginpage.phtml" + "https://www.neopets.com/loginpage.phtml" end end diff --git a/app/helpers/contribution_helper.rb b/app/helpers/contribution_helper.rb index 894066d7..da8a77d7 100644 --- a/app/helpers/contribution_helper.rb +++ b/app/helpers/contribution_helper.rb @@ -26,7 +26,7 @@ module ContributionHelper end end - PET_TYPE_IMAGE_FORMAT = 'http://pets.neopets.com/cp/%s/1/3.png' + PET_TYPE_IMAGE_FORMAT = 'https://pets.neopets.com/cp/%s/1/3.png' def contributed_pet_type(main_key, pet_type, show_image) span = content_tag(:span, pet_type.human_name, :class => 'contributed-name') description = translate('contributions.contributed_description.parents.pet_type_html', diff --git a/app/helpers/donations_helper.rb b/app/helpers/donations_helper.rb index 2121233d..e50e0849 100644 --- a/app/helpers/donations_helper.rb +++ b/app/helpers/donations_helper.rb @@ -1,18 +1,18 @@ module DonationsHelper THANK_YOU_GREETINGS = [ - 'http://images.neopets.com/new_greetings/1368.gif', - 'http://images.neopets.com/new_greetings/466.gif', - 'http://images.neopets.com/new_greetings/48.gif', - 'http://images.neopets.com/new_greetings/49.gif', - 'http://images.neopets.com/new_greetings/64.gif', - 'http://images.neopets.com/new_greetings/65.gif', - 'http://images.neopets.com/new_greetings/66.gif', - 'http://images.neopets.com/new_greetings/67.gif', - 'http://images.neopets.com/new_greetings/69.gif', - 'http://images.neopets.com/new_greetings/71.gif', - 'http://images.neopets.com/new_greetings/72.gif', - 'http://images.neopets.com/new_greetings/103.gif', - 'http://images.neopets.com/new_greetings/420.gif' + 'https://images.neopets.com/new_greetings/1368.gif', + 'https://images.neopets.com/new_greetings/466.gif', + 'https://images.neopets.com/new_greetings/48.gif', + 'https://images.neopets.com/new_greetings/49.gif', + 'https://images.neopets.com/new_greetings/64.gif', + 'https://images.neopets.com/new_greetings/65.gif', + 'https://images.neopets.com/new_greetings/66.gif', + 'https://images.neopets.com/new_greetings/67.gif', + 'https://images.neopets.com/new_greetings/69.gif', + 'https://images.neopets.com/new_greetings/71.gif', + 'https://images.neopets.com/new_greetings/72.gif', + 'https://images.neopets.com/new_greetings/103.gif', + 'https://images.neopets.com/new_greetings/420.gif' ] def thank_you_greeting_url diff --git a/app/helpers/items_helper.rb b/app/helpers/items_helper.rb index 71c19c58..0a8dd638 100644 --- a/app/helpers/items_helper.rb +++ b/app/helpers/items_helper.rb @@ -2,7 +2,7 @@ module ItemsHelper JNItemsURLFormat = 'https://items.jellyneo.net/search/?name=%s&name_type=3' module PetTypeImage - Format = 'http://pets.neopets.com/cp/%s/%i/%i.png' + Format = 'https://pets.neopets.com/cp/%s/%i/%i.png' Emotions = { :happy => 1, @@ -85,19 +85,19 @@ module ItemsHelper end def shop_wizard_url_for(item) - "http://www.neopets.com/market.phtml?type=wizard&string=#{CGI::escape item.name}" + "https://www.neopets.com/market.phtml?type=wizard&string=#{CGI::escape item.name}" end def super_shop_wizard_url_for(item) - "http://www.neopets.com/portal/supershopwiz.phtml?string=#{CGI::escape item.name}" + "https://www.neopets.com/portal/supershopwiz.phtml?string=#{CGI::escape item.name}" end def trading_post_url_for(item) - "http://www.neopets.com/island/tradingpost.phtml?type=browse&criteria=item_exact&search_string=#{CGI::escape item.name}" + "https://www.neopets.com/island/tradingpost.phtml?type=browse&criteria=item_exact&search_string=#{CGI::escape item.name}" end def auction_genie_url_for(item) - "http://www.neopets.com/genie.phtml?type=process_genie&criteria=exact&auctiongenie=#{CGI::escape item.name}" + "https://www.neopets.com/genie.phtml?type=process_genie&criteria=exact&auctiongenie=#{CGI::escape item.name}" end def trading_closet_hangers_header(owned, count) diff --git a/app/javascript/wardrobe-2020/ItemPageLayout.js b/app/javascript/wardrobe-2020/ItemPageLayout.js index 98bf92b1..38d7203e 100644 --- a/app/javascript/wardrobe-2020/ItemPageLayout.js +++ b/app/javascript/wardrobe-2020/ItemPageLayout.js @@ -159,7 +159,7 @@ function ItemPageBadges({ item, isEmbedded }) { } > {item?.ncTradeValueText && ( - + OWLS: {item?.ncTradeValueText} )} @@ -169,7 +169,7 @@ function ItemPageBadges({ item, isEmbedded }) { {!item?.isNc && !item?.isPb && ( :controller - - def expire_fragment_in_all_locales(key) - I18n.usable_locales.each do |locale| - localized_key = localize_fragment_key(key, locale) - expire_fragment(localized_key) - end - end - - def expire_key_in_all_locales(key) - I18n.usable_locales.each do |locale| - localized_key = localize_fragment_key(key, locale) - Rails.cache.delete(localized_key) - end - end - - private - - def controller - @controller ||= ActionController::Base.new - end -end diff --git a/app/models/item.rb b/app/models/item.rb index 8c171e91..08a3010f 100644 --- a/app/models/item.rb +++ b/app/models/item.rb @@ -57,11 +57,11 @@ class Item < ApplicationRecord } scope :is_nc, -> { i = Item.arel_table - where(i[:rarity_index].in(Item::NCRarities).or(i[:is_manually_nc])) + where(i[:rarity_index].in(Item::NCRarities).or(i[:is_manually_nc].eq(true))) } scope :is_np, -> { i = Item.arel_table - where(i[:rarity_index].in(Item::NCRarities).or(i[:is_manually_nc]).not) + where(i[:rarity_index].in(Item::NCRarities).or(i[:is_manually_nc].eq(true)).not) } scope :is_pb, -> { it = Item::Translation.arel_table @@ -631,8 +631,4 @@ class Item < ApplicationRecord items.values end - - def self.build_proxies(ids) - Item::ProxyArray.new(ids) - end end diff --git a/app/models/item/proxy.rb b/app/models/item/proxy.rb deleted file mode 100644 index 465d96c6..00000000 --- a/app/models/item/proxy.rb +++ /dev/null @@ -1,73 +0,0 @@ -class Item - class Proxy - include FragmentLocalization - - attr_reader :id - attr_writer :item, :owned, :wanted - - delegate :description, :name, :nc?, :thumbnail_url, :thumbnail, :to_param, to: :item - - def self.model_name - Item.model_name - end - - def initialize(item_or_id) - if item_or_id.is_a? Item - @item = item_or_id - @id = @item.id - else - @id = item_or_id.to_i - end - @known_outputs = {method: {}, partial: {}} - end - - def as_json(options={}) - cache_method(:as_json, include_hanger_status: false).tap do |json| - json[:owned] = owned? - json[:wanted] = wanted? - end - end - - def owned? - @owned - end - - def to_partial_path - # HACK: could break without warning! - Item._to_partial_path - end - - def wanted? - @wanted - end - - def fragment_key(type, name) - prefix = type == :partial ? 'views/' : '' - base = localize_fragment_key("items/#{@id}##{name}", I18n.locale) - prefix + base - end - - def set_known_output(type, name, value) - @known_outputs[type][name] = value - end - - def known_partial_output(name) - @known_outputs[:partial][name] - end - - private - - def cache_method(method_name, *args, &block) - # Two layers of cache: a local copy, in case the method is called again, - # and then the Rails cache, before we hit the actual method call. - @known_outputs[:method][method_name] ||= begin - key = fragment_key(:method, method_name) - Rails.cache.fetch(key) { item.send(method_name, *args) } - end - end - - def item - @item ||= Item.find(@id) - end - end -end \ No newline at end of file diff --git a/app/models/item/proxy_array.rb b/app/models/item/proxy_array.rb deleted file mode 100644 index 4bd41cee..00000000 --- a/app/models/item/proxy_array.rb +++ /dev/null @@ -1,56 +0,0 @@ -class Item - class ProxyArray < Array - # TODO: do we really need to include translations? The search documents - # know the proper name for each locale, so proxies can tell their - # parent items what their names are and save the query entirely. - SCOPES = HashWithIndifferentAccess.new({ - method: { - as_json: Item.includes(:translations), - } - }) - - def initialize(proxies_or_items_or_ids=[]) - self.replace(proxies_or_items_or_ids.map { |proxy_or_item_or_id| - if proxy_or_item_or_id.is_a?(Proxy) - proxy_or_item_or_id - else - Proxy.new(proxy_or_item_or_id) - end - }) - end - - def prepare_method(name) - prepare(:method, name) - end - - def prepare_partial(name) - prepare(:partial, name) - end - - private - - def prepare(type, name) - item_scope = SCOPES[type][name] - raise "unexpected #{type} #{name.inspect}" unless item_scope - - # Try to read all values from the cache in one go, setting the proxy - # values as we go along. Delete successfully set proxies, so that - # everything left in proxies_by_key in the end is known to be a miss. - proxies_by_key = {} - self.each do |p| - proxies_by_key[p.fragment_key(type, name)] ||= [] - proxies_by_key[p.fragment_key(type, name)] << p - end - Rails.cache.read_multi(*proxies_by_key.keys).each { |k, v| - proxies_by_key.delete(k).each { |p| p.set_known_output(type, name, v) } - } - - missed_proxies = proxies_by_key.values.flatten - missed_proxies_by_id = missed_proxies.index_by(&:id) - - item_scope.find(missed_proxies_by_id.keys).each do |item| - missed_proxies_by_id[item.id].item = item - end - end - end -end \ No newline at end of file diff --git a/app/models/neopets_page.rb b/app/models/neopets_page.rb index 6144a954..7ce1fafb 100644 --- a/app/models/neopets_page.rb +++ b/app/models/neopets_page.rb @@ -205,7 +205,7 @@ class NeopetsPage TYPES = { 'closet' => Type.new( get_name: lambda { I18n.translate('neopets_page_import_tasks.names.closet') }, - get_url: lambda { |index| "http://www.neopets.com/closet.phtml?per_page=50&page=#{index}" }, + get_url: lambda { |index| "https://www.neopets.com/closet.phtml?per_page=50&page=#{index}" }, parser: Parser.new( selectors: { items: "form[action=\"process_closet.phtml\"] tr[bgcolor!=silver][bgcolor!=\"#E4E4E4\"]", @@ -220,7 +220,7 @@ class NeopetsPage ), 'safety_deposit' => Type.new( get_name: lambda { I18n.translate('neopets_page_import_tasks.names.safety_deposit') }, - get_url: lambda { |index| "http://www.neopets.com/safetydeposit.phtml?offset=#{(index - 1) * 30}" }, + get_url: lambda { |index| "https://www.neopets.com/safetydeposit.phtml?offset=#{(index - 1) * 30}" }, parser: Parser.new( selectors: { items: "#content tr[bgcolor=\"#DFEAF7\"]", @@ -242,7 +242,7 @@ class NeopetsPage ), 'gallery' => Type.new( get_name: lambda { I18n.translate('neopets_page_import_tasks.names.gallery') }, - get_url: lambda { |index| "http://www.neopets.com/gallery/index.phtml?view=all" }, + get_url: lambda { |index| "https://www.neopets.com/gallery/index.phtml?view=all" }, parser: Parser.new( selectors: { items: "form[name=gallery_form] td[valign=top]", diff --git a/app/models/neopets_user.rb b/app/models/neopets_user.rb index 56b6c066..276ff89c 100644 --- a/app/models/neopets_user.rb +++ b/app/models/neopets_user.rb @@ -5,7 +5,7 @@ class NeopetsUser include ActiveModel::Conversion extend ActiveModel::Naming - NEOPETS_URL_ORIGIN = ENV['NEOPETS_URL_ORIGIN'] || 'http://www.neopets.com' + NEOPETS_URL_ORIGIN = ENV['NEOPETS_URL_ORIGIN'] || 'https://www.neopets.com' GATEWAY_URL = NEOPETS_URL_ORIGIN + '/amfphp/gateway.php' GET_PETS_METHOD = RocketAMF::RemoteGateway.new(GATEWAY_URL). service('MobileService').action('getPets') diff --git a/app/models/pet_state.rb b/app/models/pet_state.rb index e92ffe41..69b390f0 100644 --- a/app/models/pet_state.rb +++ b/app/models/pet_state.rb @@ -145,7 +145,7 @@ class PetState < ApplicationRecord def artist_url if artist_neopets_username - "http://www.neopets.com/userlookup.phtml?user=#{artist_neopets_username}" + "https://www.neopets.com/userlookup.phtml?user=#{artist_neopets_username}" else nil end diff --git a/app/models/pet_type.rb b/app/models/pet_type.rb index bd4224ec..feaea0b8 100644 --- a/app/models/pet_type.rb +++ b/app/models/pet_type.rb @@ -1,5 +1,5 @@ class PetType < ApplicationRecord - IMAGE_CPN_FORMAT = 'http://pets.neopets.com/cpn/%s/1/1.png'; + IMAGE_CPN_FORMAT = 'https://pets.neopets.com/cpn/%s/1/1.png'; IMAGE_CP_LOCATION_REGEX = %r{^/cp/(.+?)/[0-9]+/[0-9]+\.png$}; IMAGE_CPN_ACCEPTABLE_NAME = /^[a-z0-9_]+$/ diff --git a/app/views/closet_hangers/index.html.haml b/app/views/closet_hangers/index.html.haml index 39b9b0cf..b806e4b3 100644 --- a/app/views/closet_hangers/index.html.haml +++ b/app/views/closet_hangers/index.html.haml @@ -150,7 +150,7 @@ -# TODO: remove me? - content_for :stylesheets do - = stylesheet_link_tag 'http://ajax.googleapis.com/ajax/libs/jqueryui/1.9.0/themes/south-street/jquery-ui.css' + = stylesheet_link_tag 'https://ajax.googleapis.com/ajax/libs/jqueryui/1.9.0/themes/south-street/jquery-ui.css' - content_for :javascripts do = include_javascript_libraries :jquery, :jquery_tmpl diff --git a/app/views/closet_hangers/petpage.html.haml b/app/views/closet_hangers/petpage.html.haml index 2dd42d90..025f48ef 100644 --- a/app/views/closet_hangers/petpage.html.haml +++ b/app/views/closet_hangers/petpage.html.haml @@ -5,7 +5,7 @@ #intro %p= t '.description' %p= twl '.instructions', - :edit_petpage_link_url => 'http://www.neopets.com/edithomepage.phtml' + :edit_petpage_link_url => 'https://www.neopets.com/edithomepage.phtml' = form_tag petpage_user_closet_hangers_path(@user), :method => :get, :id => 'petpage-closet-lists' do = hidden_field_tag 'filter', '1' diff --git a/app/views/items/needed.html.haml b/app/views/items/needed.html.haml index 13063786..ae5516af 100644 --- a/app/views/items/needed.html.haml +++ b/app/views/items/needed.html.haml @@ -1,6 +1,6 @@ - title "Needed items for #{@pet_type.human_name}" %h2 - = image_tag "http://pets.neopets.com/cpn/#{@pet_name}/1/1.png", + = image_tag "https://pets.neopets.com/cpn/#{@pet_name}/1/1.png", :class => 'inline-image' %span.pet-name= @pet_name can model… @@ -11,6 +11,6 @@ = hidden_field_tag 'name', @pet_name = submit_tag "I'm wearing one now!", :class => 'loud' %li - = link_to 'What do I own?', 'http://www.neopets.com/closet.phtml', + = link_to 'What do I own?', 'https://www.neopets.com/closet.phtml', :class => 'button', :target => '_blank' = render @items diff --git a/app/views/layouts/application.html.haml b/app/views/layouts/application.html.haml index 3a8eb059..751ac17a 100644 --- a/app/views/layouts/application.html.haml +++ b/app/views/layouts/application.html.haml @@ -11,8 +11,6 @@ - else #{t 'app_name'}: #{t '.title_tagline'} %link{href: image_path('favicon.png'), rel: 'icon'} - /[if IE] - = include_javascript_libraries :html5 = yield :stylesheets = stylesheet_link_tag "application" = yield :meta @@ -60,8 +58,8 @@ %noscript= submit_tag 'Go' %ul - %li= link_to t('organization_name'), 'http://openneo.net/' - %li= link_to t('.footer.blog'), 'http://blog.openneo.net/' + %li= link_to t('organization_name'), 'https://openneo.net/' + %li= link_to t('.footer.blog'), 'https://blog.openneo.net/' %li= link_to t('.footer.source_code'), 'https://github.com/openneo/impress' %li= link_to t('.footer.terms'), terms_path diff --git a/app/views/layouts/items.html.haml b/app/views/layouts/items.html.haml index 2d5dcc23..151b226e 100644 --- a/app/views/layouts/items.html.haml +++ b/app/views/layouts/items.html.haml @@ -4,7 +4,7 @@ - content_for :before_flashes do %h1 = link_to items_path do - = image_tag 'http://images.neopets.com/items/mall_floatingneggfaerie.gif' + = image_tag 'https://images.neopets.com/items/mall_floatingneggfaerie.gif' %span= t 'infinite_closet' - content_for :content do = form_tag items_path, :method => :get do diff --git a/app/views/outfits/new.html.haml b/app/views/outfits/new.html.haml index 8151d1ea..f49c7e83 100644 --- a/app/views/outfits/new.html.haml +++ b/app/views/outfits/new.html.haml @@ -65,7 +65,7 @@ %li = link_to bulk_pets_path do - = image_tag 'http://images.neopets.com/items/mall_ac_garland_spotlight.gif' + = image_tag 'https://images.neopets.com/items/mall_ac_garland_spotlight.gif' %h3= link_to t('modeling_hub'), bulk_pets_path %div %h4= t '.modeling_hub.tagline' diff --git a/app/views/pets/bulk.html.haml b/app/views/pets/bulk.html.haml index ff24f50f..1e4ea308 100644 --- a/app/views/pets/bulk.html.haml +++ b/app/views/pets/bulk.html.haml @@ -68,7 +68,7 @@ %script#bulk-pets-submission-template{:type => 'text/x-jquery/tmpl'} %li.waiting - %img{:src => 'http://pets.neopets.com/cpn/${pet_name}/1/1.png'} + %img{:src => 'https://pets.neopets.com/cpn/${pet_name}/1/1.png'} %span.name ${pet_name} %span.waiting-message= t '.bulk_pets.waiting' %span.loading-message= t '.bulk_pets.loading' diff --git a/app/views/sitemap/index.xml.haml b/app/views/sitemap/index.xml.haml index ee110b35..af42187e 100644 --- a/app/views/sitemap/index.xml.haml +++ b/app/views/sitemap/index.xml.haml @@ -1,8 +1,8 @@ !!! XML -%urlset{:xmlns => "http://www.sitemaps.org/schemas/sitemap/0.9"} +%urlset{:xmlns => "https://www.sitemaps.org/schemas/sitemap/0.9"} - for item in @items %url - %loc http://#{request.host_with_port}#{url_for(item)} + %loc https://#{request.host_with_port}#{url_for(item)} %changefreq monthly %priority 0.5 diff --git a/app/views/static/image_mode.html.haml b/app/views/static/image_mode.html.haml index e6068ddc..6808f530 100644 --- a/app/views/static/image_mode.html.haml +++ b/app/views/static/image_mode.html.haml @@ -49,11 +49,11 @@ Downloading currently only works for modern browsers that support the new canvas feature. It is, however, supported in the latest versions of, - * [Google Chrome](http://www.google.com/chrome) - * [Mozilla Firefox](http://www.firefox.com/) - * [Opera](http://www.opera.com/) - * [Safari](http://www.apple.com/safari/) - * [Internet Explorer](http://www.microsoft.com/ie) + * [Google Chrome](https://www.google.com/chrome) + * [Mozilla Firefox](https://www.firefox.com/) + * [Opera](https://www.opera.com/) + * [Safari](https://www.apple.com/safari/) + * [Internet Explorer](https://www.microsoft.com/ie) However, Internet Explorer currently is having trouble running Dress to Impress in general, so is not recommended. diff --git a/bin/setup b/bin/setup index ec47b79b..3cd5a9d7 100755 --- a/bin/setup +++ b/bin/setup @@ -5,7 +5,7 @@ require "fileutils" APP_ROOT = File.expand_path("..", __dir__) def system!(*args) - system(*args) || abort("\n== Command #{args} failed ==") + system(*args, exception: true) end FileUtils.chdir APP_ROOT do diff --git a/config/application.rb b/config/application.rb index 6acd029b..4f63d2e7 100644 --- a/config/application.rb +++ b/config/application.rb @@ -9,19 +9,21 @@ Bundler.require(*Rails.groups) module OpenneoImpressItems class Application < Rails::Application # Initialize configuration defaults for originally generated Rails version. - config.load_defaults 7.0 + config.load_defaults 7.1 - # Settings in config/environments/* take precedence over those specified here. - # Application configuration should go into files in config/initializers - # -- all .rb files in that directory are automatically loaded. + # Please, add to the `ignore` list any other `lib` subdirectories that do + # not contain `.rb` files, or that should not be reloaded or eager loaded. + # Common ones are `templates`, `generators`, or `middleware`, for example. + config.autoload_lib(ignore: %w(assets tasks)) - # Set Time.zone default to the specified zone and make Active Record auto-convert to this zone. - # Run "rake -D time" for a list of tasks for finding time zone names. Default is UTC. - # config.time_zone = 'Central Time (US & Canada)' + # Configuration for the application, engines, and railties goes here. + # + # These settings can be overridden in specific environments using the files + # in config/environments, which are processed later. + # + # config.time_zone = "Central Time (US & Canada)" + # config.eager_load_paths << Rails.root.join("extras") - # The default locale is :en and all translations from config/locales/*.rb,yml are auto loaded. - # config.i18n.load_path += Dir[Rails.root.join('my', 'locales', '*.{rb,yml}').to_s] - # config.i18n.default_locale = :de config.i18n.fallbacks = true Mime::Type.register "image/gif", :gif diff --git a/config/environments/development.rb b/config/environments/development.rb index 4ed5a6fa..282a255f 100644 --- a/config/environments/development.rb +++ b/config/environments/development.rb @@ -3,10 +3,10 @@ require "active_support/core_ext/integer/time" Rails.application.configure do # Settings specified here will take precedence over those in config/application.rb. - # In the development environment your application's code is reloaded on - # every request. This slows down response time but is perfect for development + # In the development environment your application's code is reloaded any time + # it changes. This slows down response time but is perfect for development # since you don't have to restart the web server when you make code changes. - config.cache_classes = false + config.enable_reloading = true # Do not eager load code on boot. config.eager_load = false @@ -16,7 +16,7 @@ Rails.application.configure do # Enable server timing config.server_timing = true - + # Enable/disable caching. By default caching is disabled. # Run rails dev:cache to toggle caching. if Rails.root.join("tmp/caching-dev.txt").exist? @@ -25,7 +25,7 @@ Rails.application.configure do config.cache_store = :memory_store config.public_file_server.headers = { - 'Cache-Control' => "public, max-age=#{2.days.to_i}" + "Cache-Control" => "public, max-age=#{2.days.to_i}" } else config.action_controller.perform_caching = false @@ -33,16 +33,22 @@ Rails.application.configure do config.cache_store = :null_store end + # Store uploaded files on the local file system (see config/storage.yml for options). + config.active_storage.service = :local + # Don't care if the mailer can't send. config.action_mailer.raise_delivery_errors = false config.action_mailer.default_url_options = {host: "localhost", port: 3000} config.action_mailer.delivery_method = :letter_opener config.action_mailer.perform_caching = false - # Print deprecation notices to the Rails logger. - config.active_support.deprecation = :log + # Raise exceptions for disallowed deprecations. + config.active_support.disallowed_deprecation = :raise - # Raise an error on page load if there are pending migrations + # Tell Active Support which deprecation messages to disallow. + config.active_support.disallowed_deprecation_warnings = [] + + # Raise an error on page load if there are pending migrations. config.active_record.migration_error = :page_load # Debug mode disables concatenation and preprocessing of assets. @@ -53,11 +59,26 @@ Rails.application.configure do # Highlight code that triggered database queries in logs. config.active_record.verbose_query_logs = true + # Highlight code that enqueued background job in logs. + config.active_job.verbose_enqueue_logs = true + # Suppress logger output for asset requests. config.assets.quiet = true config.react.variant = :development + # Raises error for missing translations. + # config.i18n.raise_on_missing_translations = true + + # Annotate rendered view with file names. + # config.action_view.annotate_rendered_view_with_filenames = true + + # Uncomment if you wish to allow Action Cable access from any origin. + # config.action_cable.disable_request_forgery_protection = true + + # Raise error when a before_action's only/except options reference missing actions + config.action_controller.raise_on_missing_callback_actions = true + # Don't use the assets precompiled for production; recompile live instead. # HACK: We do this by just telling it that dev assets belong in a special # folder, so if you run precompile in development it'll look there instead, @@ -82,8 +103,3 @@ Rails.application.configure do # Allow connections on Vagrant's private network. config.web_console.permissions = '10.0.2.2' end - -LocalImpressHost = 'betanewimpress.openneo.net' - -RemoteImpressHost = 'beta.impress.openneo.net' - diff --git a/config/environments/production.rb b/config/environments/production.rb index 7ca1ec18..72ede57a 100644 --- a/config/environments/production.rb +++ b/config/environments/production.rb @@ -4,7 +4,7 @@ Rails.application.configure do # Settings specified here will take precedence over those in config/application.rb. # Code is not reloaded between requests. - config.cache_classes = true + config.enable_reloading = false # Eager load code on boot. This eager loads most of Rails and # your application in memory, allowing both threaded web servers @@ -16,68 +16,69 @@ Rails.application.configure do config.consider_all_requests_local = false config.action_controller.perform_caching = true - # Specifies the header that your server uses for sending files - config.action_dispatch.x_sendfile_header = "X-Sendfile" + # Ensures that a master key has been made available in ENV["RAILS_MASTER_KEY"], config/master.key, or an environment + # key such as config/credentials/production.key. This key is used to decrypt credentials (and other encrypted files). + # config.require_master_key = true - # For nginx: - # config.action_dispatch.x_sendfile_header = 'X-Accel-Redirect' + # Enable static file serving from the `/public` folder (turn off if using NGINX/Apache for it). + config.public_file_server.enabled = false - # If you have no front-end server that supports something like X-Sendfile, - # just comment this out and Rails will serve the files + # Compress CSS using a preprocessor. + # config.assets.css_compressor = :sass - # See everything in the log (default is :info) - # config.log_level = :debug + # Compress JS using a preprocessor. + config.assets.js_compressor = :terser - # Use a different logger for distributed setups - # config.logger = SyslogLogger.new + # Do not fallback to assets pipeline if a precompiled asset is missed. + config.assets.compile = false - # Use a different cache store in production - # config.cache_store = :mem_cache_store, { namespace: "openneo-impress-rails" } + # Enable serving of images, stylesheets, and JavaScripts from an asset server. + # config.asset_host = "http://assets.example.com" - # Disable Rails's static asset server - # In production, Apache or nginx will already do this - # config.serve_static_assets = true + # Specifies the header that your server uses for sending files. + # config.action_dispatch.x_sendfile_header = "X-Sendfile" # for Apache + # config.action_dispatch.x_sendfile_header = "X-Accel-Redirect" # for NGINX - # Enable serving of images, stylesheets, and javascripts from an asset server - # config.action_controller.asset_host = "http://assets.example.com" + # Store uploaded files on the local file system (see config/storage.yml for options). + config.active_storage.service = :local - # Disable delivery errors, bad email addresses will be ignored - # config.action_mailer.raise_delivery_errors = false + # Mount Action Cable outside main process or domain. + # config.action_cable.mount_path = nil + # config.action_cable.url = "wss://example.com/cable" + # config.action_cable.allowed_request_origins = [ "http://example.com", /http:\/\/example.*/ ] - # Enable threaded mode - # config.threadsafe! + # Assume all access to the app is happening through a SSL-terminating reverse proxy. + # Can be used together with config.force_ssl for Strict-Transport-Security and secure cookies. + config.assume_ssl = true # Disable serving static files from the `/public` folder by default since # Apache or NGINX already handles this. config.public_file_server.enabled = ENV['RAILS_SERVE_STATIC_FILES'].present? - - # Compress JavaScripts and CSS. - config.assets.js_compressor = :terser # Don't fallback to assets pipeline if a precompiled asset is missed config.assets.compile = false - - # Generate digests for assets URLs - config.assets.digest = true - - # Defaults to Rails.root.join("public/assets") - # config.assets.manifest = YOUR_PATH - - # Precompile additional assets (application.js, application.css, and all non-JS/CSS are already added) - # config.assets.precompile += %w( search.js ) - - # Force all access to the app over SSL, use Strict-Transport-Security, and use secure cookies. - # config.force_ssl = true - # Include generic and useful information about system operation, but avoid logging too much - # information to avoid inadvertent exposure of personally identifiable information (PII). - config.log_level = :info + # Force all access to the app over SSL, use Strict-Transport-Security, and use secure cookies. + config.force_ssl = true + + # Log to STDOUT by default + config.logger = ActiveSupport::Logger.new(STDOUT) + .tap { |logger| logger.formatter = ::Logger::Formatter.new } + .then { |logger| ActiveSupport::TaggedLogging.new(logger) } # Prepend all log lines with the following tags. config.log_tags = [ :request_id ] config.react.variant = :production + # Info include generic and useful information about system operation, but avoids logging too much + # information to avoid inadvertent exposure of personally identifiable information (PII). If you + # want to log everything, set the level to "debug". + config.log_level = ENV.fetch("RAILS_LOG_LEVEL", "info") + + # Use a different cache store in production. + # config.cache_store = :mem_cache_store + config.action_mailer.default_url_options = {host: "impress.openneo.net"} config.action_mailer.delivery_method = :smtp @@ -93,27 +94,30 @@ Rails.application.configure do config.action_mailer.raise_delivery_errors = true config.action_mailer.perform_deliveries = true config.action_mailer.perform_caching = false + + # Use a real queuing backend for Active Job (and separate queues per environment). + # config.active_job.queue_adapter = :resque + # config.active_job.queue_name_prefix = "openneo_impress_items_production" + + # Ignore bad email addresses and do not raise email delivery errors. + # Set this to true and configure the email server for immediate delivery to raise delivery errors. + # config.action_mailer.raise_delivery_errors = false # Enable locale fallbacks for I18n (makes lookups for any locale fall back to # the I18n.default_locale when a translation cannot be found). config.i18n.fallbacks = true - # Send deprecation notices to registered listeners. + # Don't log any deprecations. config.active_support.report_deprecations = false - # Use default logging formatter so that PID and timestamp are not suppressed. - config.log_formatter = ::Logger::Formatter.new - - if ENV["RAILS_LOG_TO_STDOUT"].present? - logger = ActiveSupport::Logger.new(STDOUT) - logger.formatter = config.log_formatter - config.logger = ActiveSupport::TaggedLogging.new(logger) - end - # Do not dump schema after migrations. config.active_record.dump_schema_after_migration = false + + # Enable DNS rebinding protection and other `Host` header attacks. + # config.hosts = [ + # "example.com", # Allow requests from example.com + # /.*\.example\.com/ # Allow requests from subdomains like `www.example.com` + # ] + # Skip DNS rebinding protection for the default health check endpoint. + # config.host_authorization = { exclude: ->(request) { request.path == "/up" } } end - -LocalImpressHost = 'newimpress.openneo.net' - -RemoteImpressHost = 'impress.openneo.net' diff --git a/config/environments/test.rb b/config/environments/test.rb index 6ea4d1e7..0dda9f9f 100644 --- a/config/environments/test.rb +++ b/config/environments/test.rb @@ -8,12 +8,13 @@ require "active_support/core_ext/integer/time" Rails.application.configure do # Settings specified here will take precedence over those in config/application.rb. - # Turn false under Spring and add config.action_view.cache_template_loading = true. - config.cache_classes = true + # While tests run files are not watched, reloading is not necessary. + config.enable_reloading = false - # Eager loading loads your whole application. When running a single test locally, - # this probably isn't necessary. It's a good idea to do in a continuous integration - # system, or in some way before deploying your code. + # Eager loading loads your entire application. When running a single test locally, + # this is usually not necessary, and can slow down your test suite. However, it's + # recommended that you enable it in continuous integration systems to ensure eager + # loading is working properly before deploying your code. config.eager_load = ENV["CI"].present? # Configure public file server for tests with Cache-Control for performance. @@ -28,7 +29,7 @@ Rails.application.configure do config.cache_store = :null_store # Raise exceptions instead of rendering exception templates. - config.action_dispatch.show_exceptions = false + config.action_dispatch.show_exceptions = :rescuable # Disable request forgery protection in test environment. config.action_controller.allow_forgery_protection = false @@ -57,4 +58,7 @@ Rails.application.configure do # Annotate rendered view with file names. # config.action_view.annotate_rendered_view_with_filenames = true + + # Raise error when a before_action's only/except options reference missing actions + config.action_controller.raise_on_missing_callback_actions = true end diff --git a/config/initializers/content_security_policy.rb b/config/initializers/content_security_policy.rb index 54f47cf1..b3076b38 100644 --- a/config/initializers/content_security_policy.rb +++ b/config/initializers/content_security_policy.rb @@ -16,9 +16,9 @@ # # policy.report_uri "/csp-violation-report-endpoint" # end # -# # Generate session nonces for permitted importmap and inline scripts +# # Generate session nonces for permitted importmap, inline scripts, and inline styles. # config.content_security_policy_nonce_generator = ->(request) { request.session.id.to_s } -# config.content_security_policy_nonce_directives = %w(script-src) +# config.content_security_policy_nonce_directives = %w(script-src style-src) # # # Report violations without enforcing the policy. # # config.content_security_policy_report_only = true diff --git a/config/initializers/filter_parameter_logging.rb b/config/initializers/filter_parameter_logging.rb index adc6568c..c2d89e28 100644 --- a/config/initializers/filter_parameter_logging.rb +++ b/config/initializers/filter_parameter_logging.rb @@ -1,8 +1,8 @@ # Be sure to restart your server when you modify this file. -# Configure parameters to be filtered from the log file. Use this to limit dissemination of -# sensitive information. See the ActiveSupport::ParameterFilter documentation for supported -# notations and behaviors. +# Configure parameters to be partially matched (e.g. passw matches password) and filtered from the log file. +# Use this to limit dissemination of sensitive information. +# See the ActiveSupport::ParameterFilter documentation for supported notations and behaviors. Rails.application.config.filter_parameters += [ :passw, :secret, :token, :_key, :crypt, :salt, :certificate, :otp, :ssn ] diff --git a/config/initializers/inflections.rb b/config/initializers/inflections.rb index 3860f659..7c1c0c50 100644 --- a/config/initializers/inflections.rb +++ b/config/initializers/inflections.rb @@ -14,3 +14,8 @@ # ActiveSupport::Inflector.inflections(:en) do |inflect| # inflect.acronym "RESTful" # end + +# Teach Zeitwerk that `RocketAMF` is what to expect in `lib/rocketamf`. +ActiveSupport::Inflector.inflections(:en) do |inflect| + inflect.acronym "RocketAMF" +end diff --git a/config/initializers/neopia.rb b/config/initializers/neopia.rb deleted file mode 100644 index 125c17f2..00000000 --- a/config/initializers/neopia.rb +++ /dev/null @@ -1,5 +0,0 @@ -if Rails.env.production? - Rails.configuration.neopia_host = 'neopia.openneo.net' -else - Rails.configuration.neopia_host = 'neopia.dev.openneo.net' -end \ No newline at end of file diff --git a/config/initializers/permissions_policy.rb b/config/initializers/permissions_policy.rb index 00f64d71..7db3b957 100644 --- a/config/initializers/permissions_policy.rb +++ b/config/initializers/permissions_policy.rb @@ -1,11 +1,13 @@ +# Be sure to restart your server when you modify this file. + # Define an application-wide HTTP permissions policy. For further -# information see https://developers.google.com/web/updates/2018/06/feature-policy -# -# Rails.application.config.permissions_policy do |f| -# f.camera :none -# f.gyroscope :none -# f.microphone :none -# f.usb :none -# f.fullscreen :self -# f.payment :self, "https://secure.example.com" +# information see: https://developers.google.com/web/updates/2018/06/feature-policy + +# Rails.application.config.permissions_policy do |policy| +# policy.camera :none +# policy.gyroscope :none +# policy.microphone :none +# policy.usb :none +# policy.fullscreen :self +# policy.payment :self, "https://secure.example.com" # end diff --git a/config/initializers/secret_token.rb b/config/initializers/secret_token.rb index f8754891..3e44feb0 100644 --- a/config/initializers/secret_token.rb +++ b/config/initializers/secret_token.rb @@ -9,4 +9,11 @@ # Make sure your secret_key_base is kept private # if you're sharing your code publicly. -OpenneoImpressItems::Application.config.secret_key_base = ENV.fetch('SECRET_TOKEN') +if Rails.env.development? + # In development, we use a hardcoded secret key, because it doesn't actually + # need to be secret! + OpenneoImpressItems::Application.config.secret_key_base = "7584841652f89044a8b5a428efa6dfac2461449eb24741a33668cd642130d79f93b0347766ebf4a4d7d5033a263c36431594ad56b5735a7325c8cdda991219c2" +else + # In general, we use the SECRET_TOKEN provided as an environment variable! + OpenneoImpressItems::Application.config.secret_key_base = ENV.fetch('SECRET_TOKEN') +end diff --git a/deploy/files/impress.service b/deploy/files/impress.service new file mode 100644 index 00000000..33a82e75 --- /dev/null +++ b/deploy/files/impress.service @@ -0,0 +1,29 @@ +[Unit] +Description=Dress to Impress webapp + +[Service] +User=impress +Restart=always +WorkingDirectory=/srv/impress/current +ExecStart=/opt/ruby-3.1.4/bin/bundle exec puma --port=3000 +Environment="RAILS_ENV=production" +; Set EXECJS_RUNTIME to save us from needing to install Node +Environment="EXECJS_RUNTIME=Disabled" +EnvironmentFile=/srv/impress/shared/production.env + +; Some security directives, adapted from Akkoma's service file, they seem like sensible defaults! +; Use private /tmp and /var/tmp folders inside a new file system namespace, which are discarded after the process stops. +PrivateTmp=true +; The /home, /root, and /run/user folders can not be accessed by this service anymore. If your Akkoma user has its home folder in one of the restricted places, or use one of these folders as its working directory, you have to set this to false. +ProtectHome=true +; Mount /usr, /boot, and /etc as read-only for processes invoked by this service. +ProtectSystem=full +; Sets up a new /dev mount for the process and only adds API pseudo devices like /dev/null, /dev/zero or /dev/random but not physical devices. +PrivateDevices=true +; Ensures that the service process and all its children can never gain new privileges through execve(). +NoNewPrivileges=true +; Drops the sysadmin capability from the daemon. +CapabilityBoundingSet=~CAP_SYS_ADMIN + +[Install] +WantedBy=multi-user.target \ No newline at end of file diff --git a/deploy/files/initial-placeholder/Gemfile b/deploy/files/initial-placeholder/Gemfile index a1d525e2..d924ac61 100644 --- a/deploy/files/initial-placeholder/Gemfile +++ b/deploy/files/initial-placeholder/Gemfile @@ -1,2 +1,2 @@ -source 'http://rubygems.org' +source 'https://rubygems.org' gem 'puma', '~> 6.3' \ No newline at end of file diff --git a/deploy/files/initial-placeholder/Gemfile.lock b/deploy/files/initial-placeholder/Gemfile.lock index 85651768..a6fc75df 100644 --- a/deploy/files/initial-placeholder/Gemfile.lock +++ b/deploy/files/initial-placeholder/Gemfile.lock @@ -1,11 +1,12 @@ GEM - remote: http://rubygems.org/ + remote: https://rubygems.org/ specs: nio4r (2.5.9) puma (6.3.0) nio4r (~> 2.0) PLATFORMS + x86_64-darwin-21 x86_64-linux DEPENDENCIES diff --git a/deploy/files/sites-available/impress.conf b/deploy/files/sites-available/impress.conf new file mode 100644 index 00000000..cbb3ae4f --- /dev/null +++ b/deploy/files/sites-available/impress.conf @@ -0,0 +1,44 @@ +server { + server_name {{ impress_hostname }}; + listen 80; + if ($host = {{ impress_hostname }}) { + return 301 https://$host$request_uri; + } +} + +server { + server_name {{ impress_hostname }}; + listen 443 ssl; + ssl_certificate /etc/letsencrypt/live/{{ impress_hostname }}/fullchain.pem; + ssl_certificate_key /etc/letsencrypt/live/{{ impress_hostname }}/privkey.pem; + include /etc/letsencrypt/options-ssl-nginx.conf; + ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem; + ssl_session_cache shared:SSL:10m; # https://superuser.com/q/1484466/14127 + + root /srv/impress/current/public; + + # Serve assets using their precompressed *.gz versions. + # The filenames contain content hashes, so they should be safe to + # cache forever. + # https://stackoverflow.com/a/6952804/107415 + location ~ ^/assets/ { + gzip_static on; + expires max; + add_header Cache-Control public; + add_header Last-Modified ""; + add_header ETag ""; + } + + # Try serving static files first. If not found, fall back to the app. + try_files $uri/index.html $uri @app; + + location @app { + proxy_pass http://127.0.0.1:3000; + proxy_set_header X-Real-IP $remote_addr; + proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; + proxy_set_header X-Forwarded-Proto https; + proxy_set_header X-Forwarded-Server $host; + proxy_set_header Host $http_host; + proxy_redirect off; + } +} \ No newline at end of file diff --git a/deploy/inventory.cfg b/deploy/inventory.cfg index 7a93711e..57d6f8b8 100644 --- a/deploy/inventory.cfg +++ b/deploy/inventory.cfg @@ -1,3 +1,3 @@ # There is currently only one impress box in our Ansible inventory! [webserver] -beta.impress.openneo.net +impress.openneo.net diff --git a/deploy/setup.yml b/deploy/setup.yml index 50c52d22..31bbe18a 100644 --- a/deploy/setup.yml +++ b/deploy/setup.yml @@ -5,7 +5,7 @@ become_user: root vars: email_address: "emi@matchu.dev" # TODO: Extract this to personal config? - impress_hostname: beta.impress.openneo.net + impress_hostname: impress.openneo.net tasks: - name: Create SSH folder for logged-in user become: no @@ -164,7 +164,9 @@ - name: Install system dependencies for impress's Ruby gems apt: - name: libmysqlclient-dev + name: + - libmysqlclient-dev + - libyaml-dev - name: Create the app folder file: @@ -255,37 +257,8 @@ - name: Create service file for impress copy: - dest: /etc/systemd/system/impress.service - content: | - [Unit] - Description=Dress to Impress webapp - - [Service] - User=impress - Restart=always - WorkingDirectory=/srv/impress/current - ExecStart=/opt/ruby-3.1.4/bin/bundle exec puma --port=3000 - Environment="RAILS_ENV=production" - ; Set EXECJS_RUNTIME to save us from needing to install Node - Environment="EXECJS_RUNTIME=Disabled" - EnvironmentFile=/srv/impress/shared/production.env - - ; Some security directives, adapted from Akkoma's service file, they seem like sensible defaults! - ; Use private /tmp and /var/tmp folders inside a new file system namespace, which are discarded after the process stops. - PrivateTmp=true - ; The /home, /root, and /run/user folders can not be accessed by this service anymore. If your Akkoma user has its home folder in one of the restricted places, or use one of these folders as its working directory, you have to set this to false. - ProtectHome=true - ; Mount /usr, /boot, and /etc as read-only for processes invoked by this service. - ProtectSystem=full - ; Sets up a new /dev mount for the process and only adds API pseudo devices like /dev/null, /dev/zero or /dev/random but not physical devices. - PrivateDevices=true - ; Ensures that the service process and all its children can never gain new privileges through execve(). - NoNewPrivileges=true - ; Drops the sysadmin capability from the daemon. - CapabilityBoundingSet=~CAP_SYS_ADMIN - - [Install] - WantedBy=multi-user.target + src: files/impress.service + dest: /etc/systemd/system/impress.service notify: - Reload systemctl - Restart impress @@ -310,79 +283,11 @@ classic: yes - name: Set up certbot - command: "certbot certonly --nginx -n --agree-tos --email {{ email_address }} --domains beta.impress.openneo.net" + command: "certbot certonly --nginx -n --agree-tos --email {{ email_address }} --domains {{ impress_hostname }}" - # TODO: Remove the duplication once we've fully switched over hosts! - # NOTE: I migrated over the certs manually, we'll want to have certbot - # replace them once it's recognized as impress.openneo.net! - name: Add impress config file to nginx - copy: - content: | - server { - server_name impress.openneo.net; - listen 80; - if ($host = impress.openneo.net) { - return 301 https://$host$request_uri; - } - } - - server { - server_name impress.openneo.net; - listen 443 ssl; - ssl_certificate /etc/letsencrypt/live/impress.openneo.net/fullchain.pem; - ssl_certificate_key /etc/letsencrypt/live/impress.openneo.net/privkey.pem; - include /etc/letsencrypt/options-ssl-nginx.conf; - ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem; - ssl_session_cache shared:SSL:10m; # https://superuser.com/q/1484466/14127 - - root /srv/impress/current/public; - - # Try serving static files first. If not found, fall back to the app. - try_files $uri/index.html $uri @app; - - location @app { - proxy_pass http://127.0.0.1:3000; - proxy_set_header X-Real-IP $remote_addr; - proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; - proxy_set_header X-Forwarded-Proto https; - proxy_set_header X-Forwarded-Server $host; - proxy_set_header Host $http_host; - proxy_redirect off; - } - } - - server { - server_name {{ impress_hostname }}; - listen 80; - if ($host = {{ impress_hostname }}) { - return 301 https://$host$request_uri; - } - } - - server { - server_name {{ impress_hostname }}; - listen 443 ssl; - ssl_certificate /etc/letsencrypt/live/{{ impress_hostname }}/fullchain.pem; - ssl_certificate_key /etc/letsencrypt/live/{{ impress_hostname }}/privkey.pem; - include /etc/letsencrypt/options-ssl-nginx.conf; - ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem; - ssl_session_cache shared:SSL:10m; # https://superuser.com/q/1484466/14127 - - root /srv/impress/current/public; - - # Try serving static files first. If not found, fall back to the app. - try_files $uri/index.html $uri @app; - - location @app { - proxy_pass http://127.0.0.1:3000; - proxy_set_header X-Real-IP $remote_addr; - proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; - proxy_set_header X-Forwarded-Proto https; - proxy_set_header X-Forwarded-Server $host; - proxy_set_header Host $http_host; - proxy_redirect off; - } - } + template: + src: files/sites-available/impress.conf dest: /etc/nginx/sites-available/impress.conf notify: - Restart nginx diff --git a/doc/README_FOR_APP b/doc/README_FOR_APP deleted file mode 100644 index fe41f5cc..00000000 --- a/doc/README_FOR_APP +++ /dev/null @@ -1,2 +0,0 @@ -Use this README file to introduce your application and point to useful places in the API for learning more. -Run "rake doc:app" to generate API documentation for your models, controllers, helpers, and libraries. diff --git a/lib/tasks/pet_types.rake b/lib/tasks/pet_types.rake index e3c0a116..b6ff60b1 100644 --- a/lib/tasks/pet_types.rake +++ b/lib/tasks/pet_types.rake @@ -50,7 +50,7 @@ namespace :pet_types do desc "Download the Rainbow Pool data for the given locale" task :download_basic_image_hashes => :environment do Species.find_each do |species| - pool_url = "http://www.neopets.com/pool/all_pb.phtml" + pool_url = "https://www.neopets.com/pool/all_pb.phtml" pool_options = { :cookies => {:neologin => URI.encode(ENV['NEOLOGIN'])}, :params => {:lang => 'en', :f_species_id => species.id} diff --git a/lib/tasks/translate.rake b/lib/tasks/translate.rake index 3426305b..3b14ee1d 100644 --- a/lib/tasks/translate.rake +++ b/lib/tasks/translate.rake @@ -26,7 +26,7 @@ namespace :translate do desc "Download the Rainbow Pool data for the given locale" task :pet_attributes => :environment do with_given_locale do |neopets_language_code| - pool_url = "http://www.neopets.com/pool/all_pb.phtml" + pool_url = "https://www.neopets.com/pool/all_pb.phtml" pool_options = { :cookies => {:neologin => URI.encode(ENV['NEOLOGIN'])}, :params => {:lang => neopets_language_code} diff --git a/script/rails b/script/rails deleted file mode 100755 index 9eb79100..00000000 --- a/script/rails +++ /dev/null @@ -1,9 +0,0 @@ -#!/usr/bin/env ruby1.8 -# This command will automatically be run when you run "rails" with Rails 3 gems installed from the root of your application. - -ENV_PATH = File.expand_path('../../config/environment', __FILE__) -BOOT_PATH = File.expand_path('../../config/boot', __FILE__) -APP_PATH = File.expand_path('../../config/application', __FILE__) - -require BOOT_PATH -require 'rails/commands' diff --git a/spec/controllers/broken_image_reports_controller_spec.rb b/spec/controllers/broken_image_reports_controller_spec.rb deleted file mode 100644 index 8b39ee89..00000000 --- a/spec/controllers/broken_image_reports_controller_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require 'spec_helper' - -describe BrokenImageReportsController do - -end diff --git a/spec/controllers/campaigns_controller_spec.rb b/spec/controllers/campaigns_controller_spec.rb deleted file mode 100644 index 3c06fcef..00000000 --- a/spec/controllers/campaigns_controller_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require 'spec_helper' - -describe CampaignsController do - -end diff --git a/spec/controllers/closet_hangers_controller_spec.rb b/spec/controllers/closet_hangers_controller_spec.rb deleted file mode 100644 index 6f79ab79..00000000 --- a/spec/controllers/closet_hangers_controller_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require 'spec_helper' - -describe ClosetHangersController do - -end diff --git a/spec/controllers/closet_lists_controller_spec.rb b/spec/controllers/closet_lists_controller_spec.rb deleted file mode 100644 index 075e1270..00000000 --- a/spec/controllers/closet_lists_controller_spec.rb +++ /dev/null @@ -1,19 +0,0 @@ -require 'spec_helper' - -describe ClosetListsController do - - describe "GET 'new'" do - it "should be successful" do - get 'new' - response.should be_success - end - end - - describe "GET 'create'" do - it "should be successful" do - get 'create' - response.should be_success - end - end - -end diff --git a/spec/controllers/closet_pages_controller_spec.rb b/spec/controllers/closet_pages_controller_spec.rb deleted file mode 100644 index 9f7b67ac..00000000 --- a/spec/controllers/closet_pages_controller_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require 'spec_helper' - -describe ClosetPagesController do - -end diff --git a/spec/controllers/item_zone_sets_controller_spec.rb b/spec/controllers/item_zone_sets_controller_spec.rb deleted file mode 100644 index 31b7341c..00000000 --- a/spec/controllers/item_zone_sets_controller_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require 'spec_helper' - -describe ItemZoneSetsController do - -end diff --git a/spec/controllers/items_controller_spec.rb b/spec/controllers/items_controller_spec.rb deleted file mode 100644 index b1db9fbb..00000000 --- a/spec/controllers/items_controller_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require 'spec_helper' - -describe ItemsController do - -end diff --git a/spec/controllers/pet_types_controller_spec.rb b/spec/controllers/pet_types_controller_spec.rb deleted file mode 100644 index b04bf917..00000000 --- a/spec/controllers/pet_types_controller_spec.rb +++ /dev/null @@ -1,4 +0,0 @@ -require 'spec_helper' - -describe PetTypesController do -end diff --git a/spec/controllers/swf_assets_controller_spec.rb b/spec/controllers/swf_assets_controller_spec.rb deleted file mode 100644 index 20e27a7a..00000000 --- a/spec/controllers/swf_assets_controller_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require 'spec_helper' - -describe SwfAssetsController do - -end diff --git a/spec/helpers/broken_image_reports_helper_spec.rb b/spec/helpers/broken_image_reports_helper_spec.rb deleted file mode 100644 index 2724cbc8..00000000 --- a/spec/helpers/broken_image_reports_helper_spec.rb +++ /dev/null @@ -1,15 +0,0 @@ -require 'spec_helper' - -# Specs in this file have access to a helper object that includes -# the BrokenImageReportsHelper. For example: -# -# describe BrokenImageReportsHelper do -# describe "string concat" do -# it "concats two strings with spaces" do -# helper.concat_strings("this","that").should == "this that" -# end -# end -# end -describe BrokenImageReportsHelper do - pending "add some examples to (or delete) #{__FILE__}" -end diff --git a/spec/helpers/campaigns_helper_spec.rb b/spec/helpers/campaigns_helper_spec.rb deleted file mode 100644 index 76e29d3d..00000000 --- a/spec/helpers/campaigns_helper_spec.rb +++ /dev/null @@ -1,15 +0,0 @@ -require 'spec_helper' - -# Specs in this file have access to a helper object that includes -# the CampaignsHelper. For example: -# -# describe CampaignsHelper do -# describe "string concat" do -# it "concats two strings with spaces" do -# helper.concat_strings("this","that").should == "this that" -# end -# end -# end -describe CampaignsHelper do - pending "add some examples to (or delete) #{__FILE__}" -end diff --git a/spec/helpers/closet_hangers_helper_spec.rb b/spec/helpers/closet_hangers_helper_spec.rb deleted file mode 100644 index 74eee5bb..00000000 --- a/spec/helpers/closet_hangers_helper_spec.rb +++ /dev/null @@ -1,15 +0,0 @@ -require 'spec_helper' - -# Specs in this file have access to a helper object that includes -# the ClosetHangersHelper. For example: -# -# describe ClosetHangersHelper do -# describe "string concat" do -# it "concats two strings with spaces" do -# helper.concat_strings("this","that").should == "this that" -# end -# end -# end -describe ClosetHangersHelper do - pending "add some examples to (or delete) #{__FILE__}" -end diff --git a/spec/helpers/closet_lists_helper_spec.rb b/spec/helpers/closet_lists_helper_spec.rb deleted file mode 100644 index 2678a281..00000000 --- a/spec/helpers/closet_lists_helper_spec.rb +++ /dev/null @@ -1,15 +0,0 @@ -require 'spec_helper' - -# Specs in this file have access to a helper object that includes -# the ClosetListsHelper. For example: -# -# describe ClosetListsHelper do -# describe "string concat" do -# it "concats two strings with spaces" do -# helper.concat_strings("this","that").should == "this that" -# end -# end -# end -describe ClosetListsHelper do - pending "add some examples to (or delete) #{__FILE__}" -end diff --git a/spec/helpers/closet_pages_helper_spec.rb b/spec/helpers/closet_pages_helper_spec.rb deleted file mode 100644 index 9483444d..00000000 --- a/spec/helpers/closet_pages_helper_spec.rb +++ /dev/null @@ -1,15 +0,0 @@ -require 'spec_helper' - -# Specs in this file have access to a helper object that includes -# the ClosetPagesHelper. For example: -# -# describe ClosetPagesHelper do -# describe "string concat" do -# it "concats two strings with spaces" do -# helper.concat_strings("this","that").should == "this that" -# end -# end -# end -describe ClosetPagesHelper do - pending "add some examples to (or delete) #{__FILE__}" -end diff --git a/spec/mailers/donation_mailer_spec.rb b/spec/mailers/donation_mailer_spec.rb deleted file mode 100644 index 97227bf6..00000000 --- a/spec/mailers/donation_mailer_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require "spec_helper" - -describe DonationMailer do - pending "add some examples to (or delete) #{__FILE__}" -end diff --git a/spec/models/campaign_spec.rb b/spec/models/campaign_spec.rb deleted file mode 100644 index 06d3d5ad..00000000 --- a/spec/models/campaign_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require 'spec_helper' - -describe Campaign do - pending "add some examples to (or delete) #{__FILE__}" -end diff --git a/spec/models/closet_hanger_spec.rb b/spec/models/closet_hanger_spec.rb deleted file mode 100644 index d8d2f0bb..00000000 --- a/spec/models/closet_hanger_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require 'spec_helper' - -describe ClosetHanger do - pending "add some examples to (or delete) #{__FILE__}" -end diff --git a/spec/models/closet_list_spec.rb b/spec/models/closet_list_spec.rb deleted file mode 100644 index 1e43990d..00000000 --- a/spec/models/closet_list_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require 'spec_helper' - -describe ClosetList do - pending "add some examples to (or delete) #{__FILE__}" -end diff --git a/spec/models/color_spec.rb b/spec/models/color_spec.rb deleted file mode 100644 index 1712ce9c..00000000 --- a/spec/models/color_spec.rb +++ /dev/null @@ -1,22 +0,0 @@ -require 'spec_helper' - -describe Color do - specify "should find by id, report name" do - Color.find(1).name.should == 'alien' - Color.find(2).name.should == 'apple' - end - - specify "should find by name, report id" do - Color.find_by_name('alien').id.should == 1 - Color.find_by_name('apple').id.should == 2 - end - - specify "name should be case-insensitive" do - Color.find_by_name('Alien').id.should == 1 - Color.find_by_name('alien').id.should == 1 - end - - specify "class should have list of basic colors" do - Color::Basic.map { |c| c.name }.should == ['blue', 'green', 'red', 'yellow'] - end -end diff --git a/spec/models/donation_feature_spec.rb b/spec/models/donation_feature_spec.rb deleted file mode 100644 index f7f969dc..00000000 --- a/spec/models/donation_feature_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require 'spec_helper' - -describe DonationFeature do - pending "add some examples to (or delete) #{__FILE__}" -end diff --git a/spec/models/donation_spec.rb b/spec/models/donation_spec.rb deleted file mode 100644 index bc31731a..00000000 --- a/spec/models/donation_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require 'spec_helper' - -describe Donation do - pending "add some examples to (or delete) #{__FILE__}" -end diff --git a/spec/models/item_outfit_relationship_spec.rb b/spec/models/item_outfit_relationship_spec.rb deleted file mode 100644 index f081b4b8..00000000 --- a/spec/models/item_outfit_relationship_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require 'spec_helper' - -describe ItemOutfitRelationship do - pending "add some examples to (or delete) #{__FILE__}" -end diff --git a/spec/models/item_spec.rb b/spec/models/item_spec.rb deleted file mode 100644 index dc7a5787..00000000 --- a/spec/models/item_spec.rb +++ /dev/null @@ -1,250 +0,0 @@ -require 'spec_helper' - -describe Item do - context "an item" do - before(:each) do - @item = Factory.create :item - end - - specify "should accept string or array for species_support_ids" do - @item.species_support_ids = '1,2,3' - @item.species_support_ids.should == [1, 2, 3] - @item.species_support_ids = [4, 5, 6] - @item.species_support_ids.should == [4, 5, 6] - end - - specify "should provide list of supported species objects" do - @item.species_support_ids = [1, 2, 3] - @item.supported_species.map { |s| s.name }.should == ['acara', 'aisha', 'blumaroo'] - end - - specify "should provide all species if no support ids" do - @item.species_support_ids = '' - @item.supported_species.count.should be > 0 - end - - specify "should have many swf_assets through parent_swf_asset_relationships" do - SwfAsset.delete_all - ParentSwfAssetRelationship.delete_all - 3.times do |n| - swf_asset = Factory.create :swf_asset, :id => n, :url => "http://images.neopets.com/#{n}.swf", :type => 'object' - ParentSwfAssetRelationship.create :swf_asset => swf_asset, :item => @item, :swf_asset_type => 'object' - end - dud_swf_asset = Factory.create :swf_asset, :id => 3, :type => 'object' - ParentSwfAssetRelationship.create :swf_asset => dud_swf_asset, :parent_id => 2, :swf_asset_type => 'object' - other_type_swf_asset = Factory.create :swf_asset, :id => 4, :type => 'biology' - ParentSwfAssetRelationship.create :swf_asset => other_type_swf_asset, :parent_id => 1, :swf_asset_type => 'biology' - @item.swf_assets.map(&:id).should == [0, 1, 2] - @item.swf_assets.map(&:url).should == ['http://images.neopets.com/0.swf', - 'http://images.neopets.com/1.swf', 'http://images.neopets.com/2.swf'] - end - end - - context "class" do - before :each do - Item.delete_all # don't want search returning results from previous tests - end - - specify "should search name for word" do - query_should 'blue', - :return => [ - 'A Hat That is Blue', - 'Blue Hat', - 'Blueish Hat', - 'Very Blue Hat' - ], - :not_return => [ - 'Green Hat', - 'Red Hat' - ] - end - - specify "should search name for phrase" do - query_should '"one two"', - :return => [ - 'Zero one two three', - 'Zero one two', - 'One two three' - ], - :not_return => [ - 'Zero one three', - 'Zero two three', - 'Zero one and two', - 'Three two one' - ] - end - - specify "should search name for multiple words" do - query_should 'one two', - :return => [ - 'Zero one two three', - 'Zero one two', - 'One two three', - 'Zero one and two', - 'Three two one' - ], - :not_return => [ - 'Zero one three', - 'Zero two three' - ] - end - - specify "should search name for words and phrases" do - query_should 'zero "one two" three', - :return => [ - 'zero one two three', - 'zero four one two three', - 'one two zero three', - 'three zero one two' - ], - :not_return => [ - 'one two three', - 'zero one two', - 'three one zero two', - 'two one three zero' - ] - end - - specify "should search description for words and phrases" do - query_should 'description:zero description:"one two"', - :return => [ - ['Green Hat', 'zero one two three'], - ['Blue Hat', 'five one two four zero'] - ], - :not_return => [ - 'Zero one two', - ['Zero one', 'two'], - ['Zero', 'One two'], - ['Three', 'One zero two'] - ] - end - - specify "should search by species" do - [[2],[1,2,3],[2,3],[3],[1,3]].each do |ids| - Factory.create :item, :species_support_ids => ids - end - Item.search('species:acara').count.should == 2 - Item.search('species:aisha').count.should == 3 - Item.search('species:blumaroo').count.should == 4 - end - - specify "should search by species and words" do - Factory.create :item, :name => 'Blue Hat', :species_support_ids => [1] - Factory.create :item, :name => 'Very Blue Hat', :species_support_ids => [1,2] - Factory.create :item, :name => 'Red Hat', :species_support_ids => [2] - Item.search('blue species:acara').count.should == 2 - Item.search('blue species:aisha').count.should == 1 - Item.search('red species:acara').count.should == 0 - Item.search('red species:aisha').count.should == 1 - end - - specify "should return items with no species requirements if a species condition is added" do - Factory.create :item, :species_support_ids => [1] - Factory.create :item, :species_support_ids => [1,2] - Factory.create :item, :species_support_ids => [] - Item.search('species:acara').count.should == 3 - Item.search('species:aisha').count.should == 2 - Item.search('species:acara species:aisha').count.should == 2 - Item.search('-species:acara').count.should == 0 - Item.search('-species:aisha').count.should == 1 - end - - specify "should search by only:species" do - Factory.create :item, :species_support_ids => [1], :name => 'a' - Factory.create :item, :species_support_ids => [1,2], :name => 'b' - Factory.create :item, :species_support_ids => [], :name => 'c' - Item.search('only:acara').map(&:name).should == ['a'] - Item.search('only:aisha').count.should == 0 - Item.search('-only:acara').map(&:name).should == ['b', 'c'] - Item.search('-only:aisha').map(&:name).should == ['a', 'b', 'c'] - end - - specify "should search by is:nc" do - Factory.create :item, :name => 'mall', :rarity_index => 500 - Factory.create :item, :name => 'also mall', :rarity_index => 500 - Factory.create :item, :name => 'only mall', :rarity_index => 0, :sold_in_mall => true - Factory.create :item, :name => 'not mall', :rarity_index => 400 - Factory.create :item, :name => 'also not mall', :rarity_index => 101 - Item.search('is:nc').map(&:name).should == ['mall', 'also mall', 'only mall'] - Item.search('-is:nc').map(&:name).should == ['not mall', 'also not mall'] - end - - specify "should search by is:pb" do - descriptions_by_name = { - 'Aisha Collar' => 'This item is part of a deluxe paint brush set!', - 'Christmas Buzz Hat' => 'This item is part of a deluxe paint brush set!', - 'Blue Hat' => 'This item is a trick and is NOT part of a deluxe paint brush set!', - 'Green Hat' => 'This hat is green.' - } - descriptions_by_name.each do |name, description| - Factory.create :item, :name => name, :description => description - end - Item.search('is:pb').map(&:name).should == ['Aisha Collar', 'Christmas Buzz Hat'] - Item.search('-is:pb').map(&:name).should == ['Blue Hat', 'Green Hat'] - - end - - specify "is:[not 'nc' or 'pb'] should throw ArgumentError" do - lambda { Item.search('is:nc') }.should_not raise_error(ArgumentError) - lambda { Item.search('is:pb') }.should_not raise_error(ArgumentError) - lambda { Item.search('is:awesome') }.should raise_error(ArgumentError) - end - - specify "should be able to negate word in search" do - query_should 'hat -blue', - :return => [ - 'Green Hat', - 'Red Hat', - 'Blu E Hat', - ], - :not_return => [ - 'Blue Hat', - 'Green Shirt', - 'Blue Shirt', - ] - end - - specify "should be able to negate species in search" do - Factory.create :item, :name => 'Blue Hat', :species_support_ids => [1] - Factory.create :item, :name => 'Very Blue Hat', :species_support_ids => [1,2] - Factory.create :item, :name => 'Red Hat', :species_support_ids => [1,2] - Factory.create :item, :name => 'Green Hat', :species_support_ids => [3] - Factory.create :item, :name => 'Red Shirt', :species_support_ids => [3] - Item.search('hat -species:acara').count.should == 1 - Item.search('hat -species:aisha').count.should == 2 - Item.search('hat -species:acara -species:aisha').count.should == 1 - end - - specify "should be able to negate phrase in search" do - query_should 'zero -"one two"', - :return => [ - 'Zero two one', - 'One three two zero' - ], - :not_return => [ - 'Zero one two', - 'One two three zero' - ] - end - - specify "should raise exception for a query with no conditions" do - [ - lambda { Item.search('').all }, - lambda { Item.search(nil).all }, - lambda { Item.search(' ').all } - ].each { |l| l.should raise_error(ArgumentError) } - end - - specify "should raise exception for a query that's too short" do - lambda { Item.search('e').all }.should raise_error(ArgumentError) - end - - specify "should not be able to search other attributes thru filters" do - lambda { Item.search('id:1').all }.should raise_error(ArgumentError) - end - - specify "should raise exception if species not found" do - lambda { Item.search('species:hurfdurfdurf').all }.should raise_error(ArgumentError) - end - end -end diff --git a/spec/models/outfit_spec.rb b/spec/models/outfit_spec.rb deleted file mode 100644 index f7567238..00000000 --- a/spec/models/outfit_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require 'spec_helper' - -describe Outfit do - pending "add some examples to (or delete) #{__FILE__}" -end diff --git a/spec/models/parent_swf_asset_relationship_spec.rb b/spec/models/parent_swf_asset_relationship_spec.rb deleted file mode 100644 index dc129759..00000000 --- a/spec/models/parent_swf_asset_relationship_spec.rb +++ /dev/null @@ -1,18 +0,0 @@ -require 'spec_helper' - -describe ParentSwfAssetRelationship do - context "a relationship" do - before(:each) do - @relationship = ParentSwfAssetRelationship.new - Factory.create :item, :name => 'foo' - @relationship.parent_id = 1 - end - - specify "should belong to an swf_asset" do - Factory.create :swf_asset, :type => 'object', :id => 1 - @relationship.swf_asset_id = 1 - @relationship.swf_asset.id.should == 1 - @relationship.swf_asset.type.should == 'object' - end - end -end diff --git a/spec/models/pet_state_spec.rb b/spec/models/pet_state_spec.rb deleted file mode 100644 index b7cbe19f..00000000 --- a/spec/models/pet_state_spec.rb +++ /dev/null @@ -1,18 +0,0 @@ -require 'spec_helper' - -describe PetState do - it "has many swf_assets through parent_swf_asset_relationships" do - pet_state = Factory.create :pet_state - 3.times do |n| - swf_asset = Factory.create :swf_asset, :id => n, :url => "http://images.neopets.com/#{n}.swf", :type => 'biology' - ParentSwfAssetRelationship.create :swf_asset => swf_asset, :pet_state => pet_state, :swf_asset_type => 'biology' - end - dud_swf_asset = Factory.create :swf_asset, :id => 3, :type => 'object' - ParentSwfAssetRelationship.create :swf_asset => dud_swf_asset, :parent_id => 2, :swf_asset_type => 'biology' - other_type_swf_asset = Factory.create :swf_asset, :id => 4, :type => 'biology' - ParentSwfAssetRelationship.create :swf_asset => other_type_swf_asset, :parent_id => 1, :swf_asset_type => 'object' - pet_state.swf_assets.map(&:id).should == [0, 1, 2] - pet_state.swf_assets.map(&:url).should == ['http://images.neopets.com/0.swf', - 'http://images.neopets.com/1.swf', 'http://images.neopets.com/2.swf'] - end -end diff --git a/spec/models/pet_type_spec.rb b/spec/models/pet_type_spec.rb deleted file mode 100644 index 3c42ef8a..00000000 --- a/spec/models/pet_type_spec.rb +++ /dev/null @@ -1,47 +0,0 @@ -require 'spec_helper' - -describe PetType do - context "object" do - specify "should return id, body_id in JSON" do - pet_type = PetType.create :color_id => 2, :species_id => 3, :body_id => 4 - pet_type.as_json.should == {:id => 1, :body_id => 4} - end - - specify "should allow setting species object" do - pet_type = PetType.new - pet_type.species = Species.find(1) - pet_type.species_id.should == 1 - pet_type.species.id.should == 1 - pet_type.species.name.should == 'acara' - end - - specify "should allow setting color object" do - pet_type = PetType.new - pet_type.color = Color.find(1) - pet_type.color_id.should == 1 - pet_type.color.id.should == 1 - pet_type.color.name.should == 'alien' - end - - specify "should return image hash if a basic color" do - blue = Color.find_by_name('blue') - acara = Species.find_by_name('acara') - pet_type = PetType.new :color => blue, :species => acara - pet_type.image_hash.should == 'mnbztxxn' - end - - specify "should return nil for image hash if not a basic color" do - asparagus = Color.find_by_name('asparagus') - acara = Species.find_by_name('acara') - pet_type = PetType.new :color => asparagus, :species => acara - pet_type.image_hash.should be nil - end - - specify "has many pet states" do - pet_type = Factory.create :pet_type - [1, 1, 2].each { |x| Factory.create :pet_state, :pet_type_id => x } - pet_type.pet_state_ids.should == [1, 2] - pet_type.pet_states.map(&:id).should == [1, 2] - end - end -end diff --git a/spec/models/species_spec.rb b/spec/models/species_spec.rb deleted file mode 100644 index 4889b939..00000000 --- a/spec/models/species_spec.rb +++ /dev/null @@ -1,18 +0,0 @@ -require 'spec_helper' - -describe Species do - specify "should find by id, report name" do - Species.find(1).name.should == 'acara' - Species.find(2).name.should == 'aisha' - end - - specify "should find by name, report id" do - Species.find_by_name('acara').id.should == 1 - Species.find_by_name('aisha').id.should == 2 - end - - specify "name should be case-insensitive" do - Species.find_by_name('Acara').id.should == 1 - Species.find_by_name('acara').id.should == 1 - end -end diff --git a/spec/models/swf_asset_spec.rb b/spec/models/swf_asset_spec.rb deleted file mode 100644 index 1a705641..00000000 --- a/spec/models/swf_asset_spec.rb +++ /dev/null @@ -1,35 +0,0 @@ -require 'spec_helper' - -describe SwfAsset do - it "belongs to a zone" do - asset = Factory.create :swf_asset, :zone_id => 1 - asset.zone_id.should == 1 - asset.zone.id.should == 1 - asset.zone.label.should == 'Music' - end - - it "delegates depth to zone" do - asset = Factory.create :swf_asset, :zone_id => 1 - asset.depth.should == 1 - end - - it "converts neopets URL to impress URL" do - asset = Factory.create :swf_asset, :url => 'http://images.neopets.com/cp/items/swf/000/000/012/12211_9969430b3a.swf' - asset.local_url.should == 'http://impress.openneo.net/assets/swf/outfit/items/000/000/012/12211_9969430b3a.swf' - end - - it "should contain id, depth, zone ID, and local_url as JSON" do - asset = Factory.create :swf_asset, - :id => 123, - :zone_id => 4, - :body_id => 234, - :url => 'http://images.neopets.com/cp/items/swf/000/000/012/12211_9969430b3a.swf' - asset.as_json.should == { - :id => 123, - :depth => 6, - :body_id => 234, - :local_url => 'http://impress.openneo.net/assets/swf/outfit/items/000/000/012/12211_9969430b3a.swf', - :zone_id => 4 - } - end -end diff --git a/spec/models/zone_spec.rb b/spec/models/zone_spec.rb deleted file mode 100644 index 5eb9a0dd..00000000 --- a/spec/models/zone_spec.rb +++ /dev/null @@ -1,8 +0,0 @@ -require 'spec_helper' - -describe Zone do - specify "should find by id, report label" do - Zone.find(1).label.should == 'Music' - Zone.find(3).label.should == 'Background' - end -end diff --git a/spec/spec_helper.rb b/spec/spec_helper.rb deleted file mode 100644 index 26b9118a..00000000 --- a/spec/spec_helper.rb +++ /dev/null @@ -1,32 +0,0 @@ -# This file is copied to ~/spec when you run 'ruby script/generate rspec' -# from the project root directory. -ENV["RAILS_ENV"] ||= 'test' -require File.dirname(__FILE__) + "/../config/environment" unless defined?(Rails) -require 'rspec/rails' - -# Requires supporting files with custom matchers and macros, etc, -# in ./support/ and its subdirectories. -Dir["#{File.dirname(__FILE__)}/support/**/*.rb"].each {|f| require f} - -Rspec.configure do |config| - # == Mock Framework - # - # If you prefer to use mocha, flexmock or RR, uncomment the appropriate line: - # - # config.mock_with :mocha - # config.mock_with :flexmock - # config.mock_with :rr - config.mock_with :rspec - - # If you'd prefer not to run each of your examples within a transaction, - # uncomment the following line. - # config.use_transactional_examples = false - - def query_should(query, sets) - sets.each { |k,v| sets[k] = v.map { |x| x.is_a?(Array) ? x : [x, ''] } } - all_sets = sets[:return] + sets[:not_return] - all_sets.each { |s| Factory.create :item, :name => s[0], :description => s[1]} - returned_sets = Item.search(query).all.map { |i| [i.name, i.description] }.sort - returned_sets.should == sets[:return].sort - end -end diff --git a/spec/views/closet_lists/create.html.erb_spec.rb b/spec/views/closet_lists/create.html.erb_spec.rb deleted file mode 100644 index cdb8c9b1..00000000 --- a/spec/views/closet_lists/create.html.erb_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require 'spec_helper' - -describe "closet_lists/create.html.erb" do - pending "add some examples to (or delete) #{__FILE__}" -end diff --git a/spec/views/closet_lists/new.html.erb_spec.rb b/spec/views/closet_lists/new.html.erb_spec.rb deleted file mode 100644 index 98ce1cfd..00000000 --- a/spec/views/closet_lists/new.html.erb_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require 'spec_helper' - -describe "closet_lists/new.html.erb" do - pending "add some examples to (or delete) #{__FILE__}" -end diff --git a/spec/views/petpages/new.html.erb_spec.rb b/spec/views/petpages/new.html.erb_spec.rb deleted file mode 100644 index b9434a86..00000000 --- a/spec/views/petpages/new.html.erb_spec.rb +++ /dev/null @@ -1,5 +0,0 @@ -require 'spec_helper' - -describe "petpages/new.html.erb" do - pending "add some examples to (or delete) #{__FILE__}" -end diff --git a/test/factories/item.rb b/test/factories/item.rb deleted file mode 100644 index cd71bef3..00000000 --- a/test/factories/item.rb +++ /dev/null @@ -1,15 +0,0 @@ -Factory.define :item do |i| - i.name 'Test Item' - i.description 'Test Description' - i.thumbnail_url 'http://images.neopets.com/foo.gif' - i.zones_restrict '' - i.category '' - i.add_attribute :type, '' - i.rarity 0 - i.rarity_index 0 - i.price 0 - i.weight_lbs 0 - i.species_support_ids '' - i.sold_in_mall false - i.last_spidered Time.now -end diff --git a/test/factories/pet_state.rb b/test/factories/pet_state.rb deleted file mode 100644 index 299002b4..00000000 --- a/test/factories/pet_state.rb +++ /dev/null @@ -1,4 +0,0 @@ -Factory.define :pet_state do |ps| - ps.pet_type_id 1 - ps.swf_asset_ids_cache '1,2,3' -end diff --git a/test/factories/pet_type.rb b/test/factories/pet_type.rb deleted file mode 100644 index 66ebec60..00000000 --- a/test/factories/pet_type.rb +++ /dev/null @@ -1,5 +0,0 @@ -Factory.define :pet_type do |pt| - pt.color 8 # blue - pt.species 1 # acara - pt.body_id 1 -end diff --git a/test/factories/swf_asset.rb b/test/factories/swf_asset.rb deleted file mode 100644 index ea48f253..00000000 --- a/test/factories/swf_asset.rb +++ /dev/null @@ -1,8 +0,0 @@ -Factory.define :swf_asset do |s| - s.url 'http://images.neopets.com/cp/bio/swf/000/000/000/0000_a1b2c3d4e5.swf' - s.zone_id 0 - s.zones_restrict '' - s.body_id 0 - s.add_attribute :type, 'object' - s.sequence(:id) { |n| n } -end diff --git a/tmp/restart.txt b/tmp/restart.txt deleted file mode 100644 index e69de29b..00000000 diff --git a/vendor/cache/actioncable-7.0.7.1.gem b/vendor/cache/actioncable-7.0.7.1.gem deleted file mode 100644 index 60395534..00000000 Binary files a/vendor/cache/actioncable-7.0.7.1.gem and /dev/null differ diff --git a/vendor/cache/actioncable-7.1.1.gem b/vendor/cache/actioncable-7.1.1.gem new file mode 100644 index 00000000..2d33b88c Binary files /dev/null and b/vendor/cache/actioncable-7.1.1.gem differ diff --git a/vendor/cache/actionmailbox-7.0.7.1.gem b/vendor/cache/actionmailbox-7.0.7.1.gem deleted file mode 100644 index 48d57ec2..00000000 Binary files a/vendor/cache/actionmailbox-7.0.7.1.gem and /dev/null differ diff --git a/vendor/cache/actionmailbox-7.1.1.gem b/vendor/cache/actionmailbox-7.1.1.gem new file mode 100644 index 00000000..006a4a96 Binary files /dev/null and b/vendor/cache/actionmailbox-7.1.1.gem differ diff --git a/vendor/cache/actionmailer-7.0.7.1.gem b/vendor/cache/actionmailer-7.0.7.1.gem deleted file mode 100644 index 6f66dcfa..00000000 Binary files a/vendor/cache/actionmailer-7.0.7.1.gem and /dev/null differ diff --git a/vendor/cache/actionmailer-7.1.1.gem b/vendor/cache/actionmailer-7.1.1.gem new file mode 100644 index 00000000..883d97f1 Binary files /dev/null and b/vendor/cache/actionmailer-7.1.1.gem differ diff --git a/vendor/cache/actionpack-7.0.7.1.gem b/vendor/cache/actionpack-7.0.7.1.gem deleted file mode 100644 index 097b7444..00000000 Binary files a/vendor/cache/actionpack-7.0.7.1.gem and /dev/null differ diff --git a/vendor/cache/actionpack-7.1.1.gem b/vendor/cache/actionpack-7.1.1.gem new file mode 100644 index 00000000..21e06e13 Binary files /dev/null and b/vendor/cache/actionpack-7.1.1.gem differ diff --git a/vendor/cache/actiontext-7.0.7.1.gem b/vendor/cache/actiontext-7.0.7.1.gem deleted file mode 100644 index d73e02dd..00000000 Binary files a/vendor/cache/actiontext-7.0.7.1.gem and /dev/null differ diff --git a/vendor/cache/actiontext-7.1.1.gem b/vendor/cache/actiontext-7.1.1.gem new file mode 100644 index 00000000..0d4a0e46 Binary files /dev/null and b/vendor/cache/actiontext-7.1.1.gem differ diff --git a/vendor/cache/actionview-7.0.7.1.gem b/vendor/cache/actionview-7.0.7.1.gem deleted file mode 100644 index 70d1bf19..00000000 Binary files a/vendor/cache/actionview-7.0.7.1.gem and /dev/null differ diff --git a/vendor/cache/actionview-7.1.1.gem b/vendor/cache/actionview-7.1.1.gem new file mode 100644 index 00000000..1b079bf3 Binary files /dev/null and b/vendor/cache/actionview-7.1.1.gem differ diff --git a/vendor/cache/activejob-7.0.7.1.gem b/vendor/cache/activejob-7.0.7.1.gem deleted file mode 100644 index 1149d4d7..00000000 Binary files a/vendor/cache/activejob-7.0.7.1.gem and /dev/null differ diff --git a/vendor/cache/activejob-7.1.1.gem b/vendor/cache/activejob-7.1.1.gem new file mode 100644 index 00000000..ab3f2c27 Binary files /dev/null and b/vendor/cache/activejob-7.1.1.gem differ diff --git a/vendor/cache/activemodel-7.0.7.1.gem b/vendor/cache/activemodel-7.0.7.1.gem deleted file mode 100644 index 0ba7dc5f..00000000 Binary files a/vendor/cache/activemodel-7.0.7.1.gem and /dev/null differ diff --git a/vendor/cache/activemodel-7.1.1.gem b/vendor/cache/activemodel-7.1.1.gem new file mode 100644 index 00000000..f85eeb90 Binary files /dev/null and b/vendor/cache/activemodel-7.1.1.gem differ diff --git a/vendor/cache/activerecord-7.0.7.1.gem b/vendor/cache/activerecord-7.0.7.1.gem deleted file mode 100644 index 5df2c174..00000000 Binary files a/vendor/cache/activerecord-7.0.7.1.gem and /dev/null differ diff --git a/vendor/cache/activerecord-7.1.1.gem b/vendor/cache/activerecord-7.1.1.gem new file mode 100644 index 00000000..ce782a19 Binary files /dev/null and b/vendor/cache/activerecord-7.1.1.gem differ diff --git a/vendor/cache/activestorage-7.0.7.1.gem b/vendor/cache/activestorage-7.0.7.1.gem deleted file mode 100644 index fe0605b5..00000000 Binary files a/vendor/cache/activestorage-7.0.7.1.gem and /dev/null differ diff --git a/vendor/cache/activestorage-7.1.1.gem b/vendor/cache/activestorage-7.1.1.gem new file mode 100644 index 00000000..6238a105 Binary files /dev/null and b/vendor/cache/activestorage-7.1.1.gem differ diff --git a/vendor/cache/activesupport-7.0.7.1.gem b/vendor/cache/activesupport-7.0.7.1.gem deleted file mode 100644 index 6d25477c..00000000 Binary files a/vendor/cache/activesupport-7.0.7.1.gem and /dev/null differ diff --git a/vendor/cache/activesupport-7.1.1.gem b/vendor/cache/activesupport-7.1.1.gem new file mode 100644 index 00000000..8abea39f Binary files /dev/null and b/vendor/cache/activesupport-7.1.1.gem differ diff --git a/vendor/cache/base64-0.1.1.gem b/vendor/cache/base64-0.1.1.gem new file mode 100644 index 00000000..bf37e82b Binary files /dev/null and b/vendor/cache/base64-0.1.1.gem differ diff --git a/vendor/cache/bigdecimal-3.1.4.gem b/vendor/cache/bigdecimal-3.1.4.gem new file mode 100644 index 00000000..e3266157 Binary files /dev/null and b/vendor/cache/bigdecimal-3.1.4.gem differ diff --git a/vendor/cache/devise-4.9.2.gem b/vendor/cache/devise-4.9.2.gem deleted file mode 100644 index c9b4e75a..00000000 Binary files a/vendor/cache/devise-4.9.2.gem and /dev/null differ diff --git a/vendor/cache/devise-4.9.3.gem b/vendor/cache/devise-4.9.3.gem new file mode 100644 index 00000000..e0b10b62 Binary files /dev/null and b/vendor/cache/devise-4.9.3.gem differ diff --git a/vendor/cache/diff-lcs-1.2.5.gem b/vendor/cache/diff-lcs-1.2.5.gem deleted file mode 100644 index e4436ccc..00000000 Binary files a/vendor/cache/diff-lcs-1.2.5.gem and /dev/null differ diff --git a/vendor/cache/drb-2.1.1.gem b/vendor/cache/drb-2.1.1.gem new file mode 100644 index 00000000..493cb9af Binary files /dev/null and b/vendor/cache/drb-2.1.1.gem differ diff --git a/vendor/cache/factory_girl-4.9.0.gem b/vendor/cache/factory_girl-4.9.0.gem deleted file mode 100644 index 7b55c34b..00000000 Binary files a/vendor/cache/factory_girl-4.9.0.gem and /dev/null differ diff --git a/vendor/cache/factory_girl_rails-4.9.0.gem b/vendor/cache/factory_girl_rails-4.9.0.gem deleted file mode 100644 index 94252a5a..00000000 Binary files a/vendor/cache/factory_girl_rails-4.9.0.gem and /dev/null differ diff --git a/vendor/cache/httparty-0.21.0.gem b/vendor/cache/httparty-0.21.0.gem new file mode 100644 index 00000000..7c216b03 Binary files /dev/null and b/vendor/cache/httparty-0.21.0.gem differ diff --git a/vendor/cache/io-console-0.6.0.gem b/vendor/cache/io-console-0.6.0.gem new file mode 100644 index 00000000..89d39e86 Binary files /dev/null and b/vendor/cache/io-console-0.6.0.gem differ diff --git a/vendor/cache/irb-1.8.3.gem b/vendor/cache/irb-1.8.3.gem new file mode 100644 index 00000000..3d5909a1 Binary files /dev/null and b/vendor/cache/irb-1.8.3.gem differ diff --git a/vendor/cache/jsbundling-rails-1.1.2.gem b/vendor/cache/jsbundling-rails-1.1.2.gem deleted file mode 100644 index 09bf964c..00000000 Binary files a/vendor/cache/jsbundling-rails-1.1.2.gem and /dev/null differ diff --git a/vendor/cache/jsbundling-rails-1.2.1.gem b/vendor/cache/jsbundling-rails-1.2.1.gem new file mode 100644 index 00000000..45ac1c21 Binary files /dev/null and b/vendor/cache/jsbundling-rails-1.2.1.gem differ diff --git a/vendor/cache/method_source-1.0.0.gem b/vendor/cache/method_source-1.0.0.gem deleted file mode 100644 index 2e035c34..00000000 Binary files a/vendor/cache/method_source-1.0.0.gem and /dev/null differ diff --git a/vendor/cache/multi_xml-0.6.0.gem b/vendor/cache/multi_xml-0.6.0.gem new file mode 100644 index 00000000..77c5d002 Binary files /dev/null and b/vendor/cache/multi_xml-0.6.0.gem differ diff --git a/vendor/cache/mutex_m-0.1.2.gem b/vendor/cache/mutex_m-0.1.2.gem new file mode 100644 index 00000000..bb9a0a65 Binary files /dev/null and b/vendor/cache/mutex_m-0.1.2.gem differ diff --git a/vendor/cache/psych-5.1.1.1.gem b/vendor/cache/psych-5.1.1.1.gem new file mode 100644 index 00000000..0877adf4 Binary files /dev/null and b/vendor/cache/psych-5.1.1.1.gem differ diff --git a/vendor/cache/rack-session-1.0.1.gem b/vendor/cache/rack-session-1.0.1.gem new file mode 100644 index 00000000..4d3d40e5 Binary files /dev/null and b/vendor/cache/rack-session-1.0.1.gem differ diff --git a/vendor/cache/rackup-1.0.0.gem b/vendor/cache/rackup-1.0.0.gem new file mode 100644 index 00000000..b49d5cb9 Binary files /dev/null and b/vendor/cache/rackup-1.0.0.gem differ diff --git a/vendor/cache/rails-7.0.7.1.gem b/vendor/cache/rails-7.0.7.1.gem deleted file mode 100644 index a3c7e2d0..00000000 Binary files a/vendor/cache/rails-7.0.7.1.gem and /dev/null differ diff --git a/vendor/cache/rails-7.1.1.gem b/vendor/cache/rails-7.1.1.gem new file mode 100644 index 00000000..b7f63a6d Binary files /dev/null and b/vendor/cache/rails-7.1.1.gem differ diff --git a/vendor/cache/rails-i18n-7.0.7.gem b/vendor/cache/rails-i18n-7.0.7.gem deleted file mode 100644 index 93b740cc..00000000 Binary files a/vendor/cache/rails-i18n-7.0.7.gem and /dev/null differ diff --git a/vendor/cache/rails-i18n-7.0.8.gem b/vendor/cache/rails-i18n-7.0.8.gem new file mode 100644 index 00000000..39e35c67 Binary files /dev/null and b/vendor/cache/rails-i18n-7.0.8.gem differ diff --git a/vendor/cache/railties-7.0.7.1.gem b/vendor/cache/railties-7.0.7.1.gem deleted file mode 100644 index cc0f54d7..00000000 Binary files a/vendor/cache/railties-7.0.7.1.gem and /dev/null differ diff --git a/vendor/cache/railties-7.1.1.gem b/vendor/cache/railties-7.1.1.gem new file mode 100644 index 00000000..a3c5dd98 Binary files /dev/null and b/vendor/cache/railties-7.1.1.gem differ diff --git a/vendor/cache/rdoc-6.5.0.gem b/vendor/cache/rdoc-6.5.0.gem new file mode 100644 index 00000000..ac892626 Binary files /dev/null and b/vendor/cache/rdoc-6.5.0.gem differ diff --git a/vendor/cache/reline-0.3.9.gem b/vendor/cache/reline-0.3.9.gem new file mode 100644 index 00000000..a77482a0 Binary files /dev/null and b/vendor/cache/reline-0.3.9.gem differ diff --git a/vendor/cache/responders-3.1.0.gem b/vendor/cache/responders-3.1.0.gem deleted file mode 100644 index 0e60d68b..00000000 Binary files a/vendor/cache/responders-3.1.0.gem and /dev/null differ diff --git a/vendor/cache/responders-3.1.1.gem b/vendor/cache/responders-3.1.1.gem new file mode 100644 index 00000000..b7d3c1d4 Binary files /dev/null and b/vendor/cache/responders-3.1.1.gem differ diff --git a/vendor/cache/rspec-2.0.1.gem b/vendor/cache/rspec-2.0.1.gem deleted file mode 100644 index 0d9c5161..00000000 Binary files a/vendor/cache/rspec-2.0.1.gem and /dev/null differ diff --git a/vendor/cache/rspec-core-2.0.1.gem b/vendor/cache/rspec-core-2.0.1.gem deleted file mode 100644 index 2de6ca07..00000000 Binary files a/vendor/cache/rspec-core-2.0.1.gem and /dev/null differ diff --git a/vendor/cache/rspec-expectations-2.0.1.gem b/vendor/cache/rspec-expectations-2.0.1.gem deleted file mode 100644 index 6d940364..00000000 Binary files a/vendor/cache/rspec-expectations-2.0.1.gem and /dev/null differ diff --git a/vendor/cache/rspec-mocks-2.0.1.gem b/vendor/cache/rspec-mocks-2.0.1.gem deleted file mode 100644 index b3e91ad8..00000000 Binary files a/vendor/cache/rspec-mocks-2.0.1.gem and /dev/null differ diff --git a/vendor/cache/rspec-rails-2.0.1.gem b/vendor/cache/rspec-rails-2.0.1.gem deleted file mode 100644 index 25e59bcf..00000000 Binary files a/vendor/cache/rspec-rails-2.0.1.gem and /dev/null differ diff --git a/vendor/cache/ruby2_keywords-0.0.5.gem b/vendor/cache/ruby2_keywords-0.0.5.gem new file mode 100644 index 00000000..d311c5d0 Binary files /dev/null and b/vendor/cache/ruby2_keywords-0.0.5.gem differ diff --git a/vendor/cache/stringio-3.0.8.gem b/vendor/cache/stringio-3.0.8.gem new file mode 100644 index 00000000..313c1f99 Binary files /dev/null and b/vendor/cache/stringio-3.0.8.gem differ diff --git a/vendor/cache/webrick-1.8.1.gem b/vendor/cache/webrick-1.8.1.gem new file mode 100644 index 00000000..ac0894b9 Binary files /dev/null and b/vendor/cache/webrick-1.8.1.gem differ