Trying render html entities in my express ejs Application - javascript

Here is the page I am trying to render
<% include ../partials/boilerplate %>
<div class="triviaContainer">
<h1>GAME TIME!!! </h1>
<% var i =0; data.forEach(question =>{ i+=1 %>
<div class="questionRow">
<div> <%= question.question %></div>
</div>
<div class="questionRow1">
<div clicked="" id="correctanswer<%=i %>" class="correctAnswer" > A: <%= question.correct_answer %></div>
<div clicked="" id="incorrectanswer<%=i %>" class="incorrectanswer<%=i %>" >B: <%= question.incorrect_answers[0].incorrect_answer %></div>
</div>
<div class="questionRow2">
<div clicked="" id="secondincorrectanswer<%=i %>" >C: <%= question.incorrect_answers[1].incorrect_answer %></div>
<div clicked="" id="lastanswer<%=i %>" >D: <%= question.incorrect_answers[2].incorrect_answer %></div>
</div>
<% }) %>
<form class="gameForm" method='POST' action='/trivia/score'>
<input type="hidden" name="points" value="" id="points"/>
<input type="hidden" name="gameid" value="<%= data[0].game_id %>"/>
<input type="hidden" name="questions" value="<%= data[0].number_of_questions %>"/>
<input type="submit" value="GET RESULTS">
</form>
</div>
<script type="text/javascript" src="javascript/triviaGameScript.js"></script>
<% include ../partials/end %>
I am rendering the questions in the question.question portion of the foreach function. If you look at this screen shot, the last question has a quote html entity. I have several questions that have these entities and would like to find an npm package to decode them.
Here is the controller where I am requiring html-entities npm package
const triviaModel = require('../models/trivia');
const authHelpers = require('../services/auth/auth-helpers')
const Entities = require('html-entities').XmlEntities;
const entities = new Entities();
const triviaapiController = {};
triviaapiController.index = (req, res) => {
console.log(req.body.game_id);
triviaModel.GetGame(req.body.game_id)
.then(data =>{
console.log(data);
res.render('trivia/trivia-index', {
data: data,
});
})
.catch(err => {
console.log(err);
res.status(500).json({ err });
});
}
the data portion in the trivia-index promise is where the questions and answers are stored.
here is the documentation for this particular package. https://www.npmjs.com/package/html-entities I am not specifically sure how to use it. Should I apply it in the ejs file, or to the data object that is getting passed in. Any help would be much appreciated!

You code use the package like that:
triviaapiController.index = (req, res) => {
console.log(req.body.game_id)
triviaModel.GetGame(req.body.game_id)
.then(data => {
console.log(data)
var decodedData = []
for (var q of data) {
var decodedQ = {
question: entities.decode(q.question),
correct_answer: q.correct_answer,
incorrect_answers: q.incorrect_answers
}
decodedData.push(decodedQ)
}
res.render('trivia/trivia-index', {
data: decodedData
})
})
.catch(err => {
console.log(err)
res.status(500).json({ err})
})
}

Related

?_method=DELETE is not working in this CRUD app. I am following Colt Steele's Full stack bootcamp

const methodOverride = require("method-override");
app.use(methodOverride("_method"));
app.delete("/comments/:id", (req, res) => {
const { id } = req.params;
comments = comments.filter((c) => c.id !== id);
res.redirect("/comments");
});
<h1>Comment id: <%= comment.id %></h1>
<h2><%= comment.comment %> - <%=comment.username %></h2>
Back to index
Edit Comment
Edit Comment
<form method="POST" action="/comments/ <%= comment.id %>?_method=DELETE">
<button>Delete</button>
</form>
Building a simple CRUD app and the ?_method=DELETE is not working for some reason. I am able to do everything else, however when I try to delete there is no error. The page just redirects/refreshes. Any help would be appreciated.

can't fetch data from mongodb and display that into html

model named Field.js
const mongoose = require('mongoose');
mongoose.connect('mongodb://localhost:27017/SuperchainV1', {
useNewUrlParser: true });
mongoose.set('useNewUrlParser', true);
mongoose.set('useFindAndModify', false);
mongoose.set('useCreateIndex', true);
const db = mongoose.connection;
const FieldSchema = mongoose.Schema({
productID: {
type: String
},
productName:{
type: String
},
fieldLocation: {
type: String
},
farmerName: {
type: String
},
farmerMobile: {
type: String
},
farmerNid: {
type: String
},
date: {
type: Date,
default: Date.now
}
});
const Field = mongoose.model('Field', FieldSchema);
module.exports = Field;
routes index.js
router.get('/dashboard', ensureAuthenticated, (req, res) => {
let field = Field.find({})
.sort({date:'desc'}).exec( (err, field) => {
res.render('dashboard', field);
});
})
dashboard.ejs where i want to display data after fetching
<div class="jumbotron">
<p class="lead">
<% field.productID %>
<% field.productName %>
<% field.fieldLocation %>
<% field.farmerName %>
<% field.farmerNumber %>
<% field.farmerNid %>
</p>
</div>
errors i get "field is not defined"
I want to fetch data from collections fields and display all the data into a ejs page named dashboard i tried this but always get the error field is not defined.
You need to use for loop in ejs template
<% for(var i=0; i < field.length; i++) { %>
<div class="jumbotron">
<p class="lead">
<%= field[i].productID %>
<%= field[i].productName %>
<%= field[i].fieldLocation %>
<%= field[i].farmerName %>
<%= field[i].farmerNumber %>
<%= field[i].farmerNid %>
</p>
</div>
<% } %>

Why are stripeTokens no longer being generated for my registration form?

I migrated most of Payola to Rails 5.2, and I was able to create subscriptions for users without issue up until this point. I'm puzzled at why my form is unable to generate stripeTokens and store them with the form. I receive the error stripeToken required for new customer with paid subscription. How can I fix my registration form to properly capture the stripeToken before committing the active job? I'm using the 2017 API.
UPDATE: referencing subscription_form_onestep.js. Stripe no longer allows you to use Stripe.card.createToken. I'm currently trying to see if using Stripe.createToken will work without issue.
UPDATE 2: the form is still not passing the stripeToken when the submission process begins.
UPDATE 3: It works after changing Stripe.card.createToken to Stripe.createToken and adding <%= yield(:head) %> to application.html.
registration/new.html.erb
{"guid":"74l524","status":"pending","error":null}
Server Log Error
[ActiveJob] [Payola::Worker::ActiveJob] [2597f80c-eb4c-4d51-a009-07e35668b07c] Plan Load (5.0ms) SELECT "plans".* FROM "plans" WHERE "plans"."id" = $1 LIMIT $2 [["id", 4], ["LIMIT", 1]]
[ActiveJob] [Payola::Worker::ActiveJob] [2597f80c-eb4c-4d51-a009-07e35668b07c] Payola::Subscription Exists (1.0ms) SELECT 1 AS one FROM "payola_subscriptions" WHERE "payola_subscriptions"."guid" = $1 AND "payola_subscriptions"."id" != $2 LIMIT $3 [["guid", "gjfsnd"], ["id", 49],
["LIMIT", 1]]
[ActiveJob] [Payola::Worker::ActiveJob] [2597f80c-eb4c-4d51-a009-07e35668b07c] Payola::Subscription Update (1.0ms) UPDATE "payola_subscriptions" SET "error" = $1, "updated_at" = $2 WHERE "payola_subscriptions"."id" = $3 [["error", "stripeToken required for new customer with paid subscription"], ["updated_at", "2019-02-24 15:10:20.714048"],
["id", 49]]
[ActiveJob] [Payola::Worker::ActiveJob] [2597f80c-eb4c-4d51-a009-07e35668b07c] PaperTrail::Version Create (1.0ms) INSERT INTO "versions" ("item_type", "item_id", "event", "object", "created_at")
subscription_form_onestep.js
var PayolaOnestepSubscriptionForm = {
initialize: function () {
$(document).off('submit.payola-onestep-subscription-form').on(
'submit.payola-onestep-subscription-form', '.payola-onestep-subscription-form',
function () {
return PayolaOnestepSubscriptionForm.handleSubmit($(this));
}
);
},
handleSubmit: function (form) {
if (!PayolaOnestepSubscriptionForm.validateForm(form)) {
return false;
}
$(form).find("input[type=submit]").prop("disabled", true);
$('.payola-spinner').css('visibility', 'visible');
Stripe.card.createToken(form, function (status, response) {
PayolaOnestepSubscriptionForm.stripeResponseHandler(form, status, response);
});
return false;
},
validateForm: function (form) {
var cardNumber = $("input[data-stripe='number']").val();
if (!Stripe.card.validateCardNumber(cardNumber)) {
PayolaOnestepSubscriptionForm.showError(form, 'The card number is not a valid credit card number.');
return false;
}
if ($("[data-stripe='exp']").length) {
var valid = !Stripe.card.validateExpiry($("[data-stripe='exp']").val());
} else {
var expMonth = $("[data-stripe='exp_month']").val();
var expYear = $("[data-stripe='exp_year']").val();
var valid = !Stripe.card.validateExpiry(expMonth, expYear);
}
if (valid) {
PayolaOnestepSubscriptionForm.showError(form, "Your card's expiration month/year is invalid.");
return false
}
var cvc = $("input[data-stripe='cvc']").val();
if (!Stripe.card.validateCVC(cvc)) {
PayolaOnestepSubscriptionForm.showError(form, "Your card's security code is invalid.");
return false;
}
return true;
},
stripeResponseHandler: function (form, status, response) {
if (response.error) {
PayolaOnestepSubscriptionForm.showError(form, response.error.message);
} else {
var email = form.find("[data-payola='email']").val();
var coupon = form.find("[data-payola='coupon']").val();
var quantity = form.find("[data-payola='quantity']").val();
var base_path = form.data('payola-base-path');
var plan_type = form.data('payola-plan-type');
var plan_id = form.data('payola-plan-id');
var action = $(form).attr('action');
form.append($('<input type="hidden" name="plan_type">').val(plan_type));
form.append($('<input type="hidden" name="plan_id">').val(plan_id));
console.log(response.id + "stripeToken Value DEBUG");
form.append($('<input type="hidden" name="stripeToken">').val(response.id));
form.append($('<input type="hidden" name="stripeEmail">').val(email));
form.append($('<input type="hidden" name="coupon">').val(coupon));
form.append($('<input type="hidden" name="quantity">').val(quantity));
form.append(PayolaOnestepSubscriptionForm.authenticityTokenInput());
$.ajax({
type: "POST",
url: action,
data: form.serialize(),
success: function (data) {
PayolaOnestepSubscriptionForm.poll(form, 60, data.guid, base_path);
},
error: function (data) {
PayolaOnestepSubscriptionForm.showError(form, jQuery.parseJSON(data.responseText).error);
}
});
}
},
poll: function (form, num_retries_left, guid, base_path) {
if (num_retries_left === 0) {
PayolaOnestepSubscriptionForm.showError(form, "This seems to be taking too long. Please contact support and give them transaction ID: " + guid);
}
var handler = function (data) {
if (data.status === "active") {
window.location = base_path + '/confirm_subscription/' + guid;
} else {
setTimeout(function () {
PayolaOnestepSubscriptionForm.poll(form, num_retries_left - 1, guid, base_path);
}, 500);
}
};
var errorHandler = function (jqXHR) {
PayolaOnestepSubscriptionForm.showError(form, jQuery.parseJSON(jqXHR.responseText).error);
};
if (typeof guid != 'undefined') {
$.ajax({
type: 'GET',
dataType: 'json',
url: base_path + '/subscription_status/' + guid,
success: handler,
error: errorHandler
});
}
},
showError: function (form, message) {
$('.payola-spinner').css("visibility", "hidden");
$(form).find("input[type=submit]").prop('disabled', false).trigger('error', message);
var error_selector = form.data('payola-error-selector');
if (error_selector) {
$(error_selector).text(message);
$(error_selector).show();
} else {
form.find('.payola-payment-error').text(message);
form.find('.payola-payment-error').show();
}
},
authenticityTokenInput: function () {
return $('<input type="hidden" name="authenticity_token"></input>').val($('meta[name="csrf-token"]').attr("content"));
}
};
PayolaOnestepSubscriptionForm.initialize();
routes.rb
scope module: 'payola' do
post 'payola/buy/:product_class/:permalink' => 'transactions#create', as: :buy
get 'payola/confirm/:guid' => 'transactions#show', as: :confirm
get 'payola/status/:guid' => 'transactions#status', as: :status
post 'payola/subscribe/:plan_class/:plan_id' => 'subscriptions#create', as: :subscribe
get 'payola/confirm_subscription/:guid' => 'subscriptions#show', as: :confirm_subscription
get 'payola/subscription_status/:guid' => 'subscriptions#status', as: :subscription_status
delete 'payola/cancel_subscription/:guid' => 'subscriptions#destroy', as: :cancel_subscription
post 'payola/change_plan/:guid' => 'subscriptions#change_plan', as: :change_subscription_plan
post 'payola/change_quantity/:guid' => 'subscriptions#change_quantity', as: :change_subscription_quantity
post 'payola/update_card/:guid' => 'subscriptions#update_card', as: :update_card
post 'payola/update_customer/:id' => 'customers#update', as: :update_customer
post 'payola/create_card/:customer_id' => 'cards#create', as: :create_card
delete 'payola/destroy_card/:id/:customer_id' => 'cards#destroy', as: :destroy_card
mount StripeEvent::Engine => '/events'
end
new.html.erb
<% content_for :head do %>
<%= render 'payola/transactions/stripe_header' %>
<% end %>
<div class="container">
<div class="form-padding-top">
<%= form_for(resource, :as => resource_name, :url => registration_path(resource_name), :html => {
:class => 'payola-onestep-subscription-form',
'data-payola-base-path' => payola_path,
'data-payola-plan-type' => resource.plan.plan_class,
'data-payola-plan-id' => resource.plan.id}) do |f| %>
<div class="form-group">
<div class="col-md-8">
<%= devise_error_messages! %>
<span id="error_explanation" class="payola-payment-error"></span>
</div>
</div>
<fieldset class="form-group">
<legend><strong>Sign up</legend>
</fieldset>
<div class="form-group">
<div class="col-md-4">
<label>Select a plan for your company</label>
<%= f.collection_select(:plan_id, Plan.user_plan, :id, :name, {}, {:class => 'form-control'}) %>
</div>
</div>
<div class="form-group">
<label for="fg-1" class="col-md-5 col-form-label">Email</label>
<div class="col-md-5">
<%= f.email_field :email, label: false, required: true, autofocus: true, placeholder: 'What is your email address?', class: 'form-control' %>
</div>
</div>
<div class="form-group">
<label class="col-md-5 col-form-label">Username</label>
<div class="col-md-5">
<span class="username-icon-styles">
<span id="valid-username" class="fa fa-check-circle"></span>
<span id="invalid-username" class="fa fa-times-circle"></span>
</span>
<%= f.text_field :username, label: false, required: true, placeholder: 'Create a username for your account', class: 'form-control' %>
</div>
</div>
<p class="status" style="display: block;">
<span class="status_icon"></span>
<span class="status_message"></span>
</p>
</div>
</div>
</div>
<div class="form-group">
<div class="col-md-2">
<label>CVC</label>
<%= text_field :card_code, nil, name: nil, class: 'form-control', data: {stripe: 'cvc'}, placeholder: '000', maxlength: 3 %>
</div>
</div>
<br/>
<div class="form-group">
<div class="col-md-2">
<label>Card Expiration</label>
<%= select_month nil, {use_two_digit_numbers: true}, {name: nil, data: {stripe: 'exp_month'}, class: 'form-control'} %>
<%= select_year nil, {start_year: Date.today.year, end_year: Date.today.year + 10}, {name: nil, data: {stripe: 'exp_year'}, class: 'form-control'} %>
</div>
</div>
<div class="form-group">
<div class="col-md-5">
<label>Password</label>
<%= f.password_field :password, required: true, hint: ("#{#minimum_password_length} characters minimum, include special characters #!%$& and capital letters" if #minimum_password_length), class: 'form-control', label: false %>
</div>
</div>
<div class="form-group">
<div class="col-md-5">
<label for="password-confirm">Password Confirm</label>
<%= f.password_field :password_confirmation, required: true, label: false, class: 'form-control' %>
</div>
</div>
<%= f.submit "Sign up", :class => 'bttn-material-flat bttn-md bttn-primary button', data: {disable_with: false} %>
<div class="text-center">
<div class="payola-spinner">Loading…</div>
</div>
<% end %>
registrations_controller.rb
class Users::RegistrationsController < Devise::RegistrationsController
include Payola::StatusBehavior
before_action :cancel_subscription, only: [:destroy]
def new
build_resource({})
unless params[:plan].nil?
#plan = Plan.find_by!(stripe_id: params[:plan])
resource.plan = #plan
end
yield resource if block_given?
respond_with resource
end
def create
build_resource(sign_up_params)
plan = Plan.find_by!(id: params[:user][:plan_id].to_i)
resource.role = User.roles[plan.stripe_id]
resource.save
yield resource if block_given?
if resource.persisted?
if resource.active_for_authentication?
set_flash_message :notice, :signed_up if is_flashing_format?
sign_up(resource_name, resource)
subscribe
else
set_flash_message :notice, :"signed_up_but_#{resource.inactive_message}" if is_flashing_format?
expire_data_after_sign_in!
subscribe
end
else
clean_up_passwords resource
resource.errors.full_messages.each {|i| flash[i] = i}
end
end
def user_change_plan
plan = Plan.find_by!(id: params[:user][:plan_id].to_i)
unless plan == current_user.plan
role = User.roles[plan.stripe_id]
if current_user.update_attributes!(plan: plan, role: role)
subscription = Payola::Subscription.find_by!(owner_id: current_user.id)
Payola::ChangeSubscriptionPlan.call(subscription, plan)
redirect_to edit_user_registration_path, notice: 'Plan changed.'
else
flash[:alert] = 'Unable to change plan.'
build_resource
render :edit
end
end
end
def user_change_credit_card
#subscription = Payola::Subscription.find_by!(owner_id: current_user.id)
if #subscription.save
Payola::UpdateCard.call(#subscription, params[:stripeToken])
redirect_to edit_user_registration_path, notice: 'Your Credit Card Was Successfully Updated.'
else
build_resource
redirect_to edit_user_registration_path, notice: "There was an error, please check for mistakes with your card information"
end
end
def cancel_user_subscription
#subscription = Payola::Subscription.find_by!(owner_id: current_user.id, state: 'active')
if #subscription.save
Payola::CancelSubscription.call(#subscription) if !#subscription.nil?
current_user.plan_id = nil
current_user.deactivated = true
current_user.save
redirect_to edit_user_registration_path, notice: "Your Plan was Successfully Cancelled."
else
build_resource
redirect_to edit_user_registration_path, notice: "Something went wrong, please try again."
end
end
private
def after_update_path_for(resource)
authenticated_user_root_path
end
def after_sign_up_path_for(resource)
u_dashboard_index_path
end
def subscribe
params[:plan] = current_user.plan
params[:stripeEmail] = current_user.email
params[:trial_start] = DateTime.now
params[:trial_end] = DateTime.now + 6.days
subscription = Payola::CreateSubscription.call(params, current_user)
current_user.save
render_payola_status(subscription)
end
end

Can't get username from req.user to output in express

I'm using ejs to try to output a username from req.user in a node express app, but it doesn't seem to be working.
This is where my username and password come in:
app.get('/', function(req, res) {
res.render('index', {
isAuthenticated: req.isAuthenticated(),
user: req.user
});
console.log("req.user:", req.user);
});
At this point, I can see req.user in terminal displayed like this:
req.user: [ { _id: 5890f8a97ef995525d4b78cd,
username: 'dave',
password: 'somepassword',
__v: 0 } ]
This is what I have in index.ejs:
<!DOCTYPE html>
<html>
<head>
<title>Login</title>
<head>
<body>
<% if (!isAuthenticated) { %>
Log in here
<% } else { %>
Hello, <%= user.username %>!
Log out
<% } %>
</body>
</html>
And this is the login form:
<!DOCTYPE html>
<html>
<head>
<title>Passport</title>
<head>
<body>
<form action="" method="post">
<input type="text" name="username" placeholder="Username">
<input type="password" name="password" placeholder="Password">
<input type="submit" value="Login">
</form>
</body>
</html>
I initially had this in my index.ejs, but still did not output username.
Hello, <%= user.name %>!
Would appreciate any help.
Based on what your terminal displayed, it looks like req.user is an array containing objects, which means that you would need to access one of the elements in the array before accessing the object's properties.
Therefore <%= user.username %> would be <%= user[0].username %>:
<% if (!isAuthenticated) { %>
Log in here
<% } else { %>
Hello, <%= user[0].username %>!
Log out
<% } %>
Or you could just update the web service to pass in the first element in the user array:
res.render('index', {
isAuthenticated: req.isAuthenticated(),
user: req.user[0]
});
<% if (!isAuthenticated) { %>
Log in here
<% } else { %>
Hello, <%= user.username %>!
Log out
<% } %>
You may also want to check if the user array contains any elements to prevent any errors from being thrown if it doesn't:
res.render('index', {
isAuthenticated: req.isAuthenticated(),
user: (req.user && req.user.length) ? req.user[0] : {}
});

How to pass html values in Ruby within a Javascript function

I have a view page, where the user inputs a number and clicks on generate to get a form in the same page based on this input. So I'm using javascript in my main view:
<div class="label-field-pair"><%= "#{t('total')} #{t('amount')}" %>:
<%= form.text_field :total, :value =>precision_label(#total_pay.to_f) , :disabled=> true , :id=>'total' %></div>
<div class="label-field-pair">
<label for="student_grade"><%= t('no_payments') %><span class="necessary-field">*</span> </label>
<input type="number" min="1" max="12" step="1" value="1" name="no_payments" id="no_payments"> </div>
<%= form.hidden_field :no_payments, :id=>'payments' %>
<%= form.hidden_field :total_pay, :id=>'total_pay' %>
<%#= submit_tag "", :value => "► #{t('generate')}", :class => "submit_button", :disable_with => "► #{t('please_wait')}" %>
<%#= render :partial => 'distribute_payments', :locals => {:no_payments=>2, :total => 30000 , :guardian=>#guardian.id} %>
<button type="button" id="gen" onClick="generate()" style="display: block">Generate</button>
<div id="payments_distribute"></div>
<%end%>
<script type="text/javascript">
function generate() {
var t = document.getElementById("total").value;
var n = document.getElementById("no_payments").value;
j('#total_pay').val("<%= #total_pay %>");
document.getElementById("gen").style.display = "none";
<%="#{remote_function(:url => {:action => "distribute_payments", :id=>#guardian.id,:total_pay=>#total_pay}
)}"%>
}
</script>
And this is the action for my partial view:
def distribute_payments
#total_amount=params[:total]
#no_payments=params[:no_payments]
#total_payment=params[:total_pay]
#guardian = Guardian.find(params[:id])
#students=Student.find_all_by_sibling_id(#guardian.ward_id)
render(:update) do |page|
page.replace_html 'payments_distribute', :partial=>'distribute_payments', :total_pay=>#total_payment, :no_payments=>#no_payments
end
end
The problem here is that I need to pass the value of "no_payments" with the parameters to my partial view, and I don't know how to do this from my Javascript function (remote_function). I was trying to use render_partial with a submit button, but I wasn't able to open the partial view in the same page. You can check my question here: Rails: Render Partial from controller
You need to use Ajax:
<script type="text/javascript">
function generate() {
var t = document.getElementById("total").value;
var n = document.getElementById("no_payments").value;
var id="<%= #guardian.id %>"
j('#total_pay').val("<%= #total_pay %>");
document.getElementById("gen").style.display = "none";
j.ajax({
type: 'POST' ,
url: '<%= url_for :action => "distribute_payments" %>',
data : {
'no_payments' :n,
'total_payment' :t,
'id' :id
},
beforeSend : function() {
},
success : function() {
j("#payments_distribute").html(data)
}});
}
</script>

Categories

Resources