I'm using MVC and am trying to check if the item has enough stock in inventory. I do this in my controller by
[HttpPost]
[ValidateAntiForgeryToken]
[Audit]
public void AddUnits(int so_id, int site_id, int[] addItem_id, int[] addItem_qty)
{
// Loop however many times is necessary to iterate through the largest array
for (int i = 0; i < Math.Max(Math.Max(addItem_id.Length, addComp_id.Length), addPart_id.Length); i++)
{
foreach (SODetails sod in db.SalesOrders.Find(so_id).SalesDetails)
{
if (i < addItem_id.Length && addItem_qty[i] != 0 && sod.ItemID == addItem_id[i] && addItem_id[i] != 365 && addItem_id[i] != 410)
{
sod.item_qty += addItem_qty[i];
sod.item_discount = addItem_disc[i];
addItem_id[i] = 0;
addItem_qty[i] = 0;
addItem_disc[i] = 0;
}
}
db.SaveChanges();
if(i < addItem_qty.Length && addItem_qty[i] != 0)
{
SODetails sODetails = new SODetails
{
SalesOrderID = so_id,
SiteID = site_id
};
// Only add a unit to the SODetails object if it's not null and has an id and quanitity specified
if(i < addItem_id.Length && addItem_id[i] != 0 && addItem_qty[i] != 0)
{
sODetails.ItemID = addItem_id[i];
sODetails.item_qty = addItem_qty[i];
sODetails.item_discount = addItem_disc[i];
}
SalesOrder SO = db.SalesOrders.Find(sODetails.SalesOrderID);
SODetails salesOrderDetails = db.SODetails.Add(sODetails);
salesOrderDetails.SalesOrder = SO;
Item SO_Item = db.Items.Find(sODetails.ItemID);
if (SO_Item != null)
{
ViewBag.itemOnHand = SO_Item.On_Hand;
sODetails.item_qty = sODetails.item_qty == null ? 0 : sODetails.item_qty;
int qtyOrdered = sODetails.item_qty == null ? 0 : (int)sODetails.item_qty;
salesOrderDetails.dynamicItem_qty = qtyOrdered;
if (SO_Item.SalesOrderMessage != null)
TempData["SalesOrderMessage"] = SO_Item.SalesOrderMessage;
}
}
}
}
db.SaveChanges();
}
Currently I'm trying to pass the inventory count of that item into the viewbag by doing
ViewBag.itemOnHand = SO_Item.On_Hand;
Then my view Jquery function looks like this
// Get all item ids and quantities and store them in arrays
var itemssel = document.getElementsByClassName("Item-select");
var itemsqtysel = document.getElementsByClassName("Item-qty");
var itemsdiscsel = document.getElementsByClassName("Item-disc");
var itemOnHand = #ViewBag.itemOnHand;
for (i = 0; i < itemssel.length; i++) {
items[i] = itemssel[i].options[itemssel[i].selectedIndex].value;
itemsqty[i] = itemsqtysel[i].value;
itemsdisc[i] = itemsdiscsel[i].value;
if (itemsqty[i] < 0) {
alert("Quantities can't be negative!");
return;
}
if (itemsqty[i] < itemOnHand) {
alert("Not enough inventory in site!");
return;
}
// The add units method is then called here
// Send all the values to the AJAX function and respond with success or error
$.ajax({
type: "POST",
url: "#IGT.baseUrl/SODetailsAjax/AddUnits",
traditional: true,
data: {
__RequestVerificationToken: token,
so_id: #Int32.Parse(Request["orderId"]),
site_id: site,
addItem_id: items,
addItem_qty: itemsqty,
addItem_disc: itemsdisc,
addComp_id: comps,
addComp_qty: compsqty,
addComp_disc: compsdisc,
addPart_id: parts,
addPart_qty: partsqty,
addPart_disc: partsdisc
},
success: function () {
location.href = "../SalesOrders/Details?id=#so.ID";
},
error: function (jqXHR, status, error) {
alert("Error: " + error);
}
});
But it doesn't work correctly as it is right now. Why is this?
As requested, here is my GET method for the page before it posts
// GET: SODetails/Create
[RestrictAccess(restriction = AccessRestrictions.ModifySalesOrder)]
public ActionResult Create(int orderId)
{
var SOID = (from i in db.SalesOrders.Where(x => x.ID == orderId).Where(x => x.deleted == false)
select new
{
SO_id = i.ID,
status = i.ID + " (Status: " + i.SalesOrderStatus +")",
}).OrderByDescending(x => x.SO_id).ToList();
var item = (from i in db.Items.Where(x => x.deleted == false)
select new
{
itemID = i.ID,
itemName = i.Product_Number + " : " + i.ItemID + " : " + i.Name
}).OrderBy(x => x.itemName).ToList();
var component = (from c in db.Components.Where(x => x.deleted == false)
select new
{
compID = c.ID,
compName = c.Product_Number + " : " + c.ComponentID + " : " + c.Name
}).OrderBy(x => x.compName).ToList();
var part = (from c in db.Parts.Where(x => x.deleted == false)
select new
{
partID = c.ID,
partName = c.Product_Number + " : " + c.PartID + " : " + c.Name
}).OrderBy(x => x.partName).ToList();
var sites = (from s in db.Sites
select new
{
siteID = s.ID,
siteName = s.Name
}).OrderBy(x => x.siteName).ToList();
sites.Insert(0, new { siteID = 0, siteName = "Main Inventory" });
var masters = db.Items.Where(x => x.Product_Number.Contains("106101") || x.ItemID.Contains("106101"));
List<int> ids = new List<int>();
foreach(Item i in masters.Where(x => x.Product_Number.Contains("BMU") || x.Product_Number.Contains("BMDU") || x.Product_Number.Contains("BMS")))
{
ids.Add(i.ID);
}
ViewBag.BMUMasters = ids.ToArray();
ids = new List<int>();
foreach (Item i in masters.Where(x => x.Product_Number.Contains("GMU")))
{
ids.Add(i.ID);
}
ViewBag.GMUMasters = ids.ToArray();
ViewBag.ItemID = new SelectList(item, "itemID", "itemName");
ViewBag.ComponentID = new SelectList(component, "compID", "compName");
ViewBag.PartID = new SelectList(part, "partID", "partName");
ViewBag.SalesOrderID = new SelectList(SOID, "SO_id", "status");
ViewBag.SiteID = new SelectList(sites, "siteID", "siteName");
ViewBag.invSiteID = new SelectList(sites, "siteID", "siteName");
return View();
}
Try to add null coalescing, this will return 0 if the ViewBag.itemOnHand is empty;
var itemOnHand = #(ViewBag.itemOnHand ?? 0);
Then if you're going to use it for some number operations try to force it to become an integer;
var itemOnHand = Number(#(ViewBag.itemOnHand ?? 0));
Since you already have an if statement or null checks prior to ViewBag assignment, you could simply return the view and add a ViewBag.Error;
if (SO_Item != null)
{
// .. if not null
}else{
// if null return view
ViewBag.Error = "your error here";
return View();
}
Then somewhere in your view add this;
#if(ViewBag.Error != null){
<div class="row error">
<div class="col-md-12">
Error occured: <strong>#ViewBag.Error</strong>
</div>
</div>
}
Related
I am trying to parse pdf datas asynchronously, then populate a JS object with the content of the pdf file, and then return it in a Promise.
I am using the "pdfreader" module and its method parseFileItems()
async function parsePdfDatas(filePath){
var output = {};
var reader = new pdfreader.PdfReader();
await reader.parseFileItems(filePath, function(err, item) {
// item treatment populating output Object
});
return output;
}
parsePdfDatas("./****.pdf").then( function(output) {
console.log(output);
});
The await statement doesn't work, anybody get an idea ?
EDIT
After xMayank answer, i tried as follows, which doesn't work neither:
const fs = require('fs');
var pdfreader = require("pdfreader");
var row = {
id: "",
muban: "",
get mID() {
this.id.slice(6,8);
},
tambon: "",
get tID() {
this.id.slice(4,6);
},
amphoe: "",
get aID() {
this.id.slice(2,4);
},
changwat: "",
get cID() {
this.id.slice(0,2);
}
}
function parsePdfDatas(filePath){
return new Promise(function(resolve, reject){
var output = {};
var reader = new pdfreader.PdfReader();
reader.parseFileItems(filePath, function(err, item) {
if(item && item.text && item.text.match(/^-{1,3}[0-9]{1,4}-{1,3}$/) === null && item.y != 2.887){
if(item.x === 2.388){
// If the row object contains a muban entry, we push it at the end of output
if(row.id !== ""){
//console.log(row);
output[row.id] = {mName : row.muban, tName : row.tambon, aName : row.amphoe, cName : row.changwat};
}
// new line, row object reinitialization
row.id = row.muban = row.tambon = row.amphoe = row.changwat = "";
}
// correction for ่ ้
if(item.R[0].T === "%E0%B8%BD") item.text = "่";
if(item.R[0].T === "%E0%B8%BE") item.text = "้";
if(item.x >= 2.388 && item.x < 11.303)
row.id += item.text;
else if(item.x >= 11.303 && item.x < 17.969)
row.muban += item.text;
else if(item.x >= 17.969 && item.x < 23.782)
row.tambon += item.text;
else if(item.x >= 23.782 && item.x < 29.698)
row.amphoe += item.text;
else if(item.x >= 29.698)
row.changwat += item.text;
console.log(item.R[0].T + " -> " + item.text);
//console.log(item.text + " : x = " + item.x + " | y = " + item.y);
}
});
resolve(output);
});
}
parsePdfDatas("./files/mubans0.pdf").then((output) => {
console.log(output);
});
Works fine.
const { PdfReader } = require("pdfreader");
function readFile(file){
return new Promise(function(resolve, reject){
new PdfReader().parseFileItems(file, function(err, item) {
if (err) reject(err);
else if (!item) resolve();
else if (item.text) resolve(item.text);
});
})
}
readFile("./****.pdf")
.then(result =>{
console.log("Here", result)
})
I have a problem with delete object from my json file:
{
"data": [{
"index": "1",
"part": "15",
"dueDate": "2019-03-19"
}]
}, {
"data": [{
"index": "2",
"part": "22",
"dueDate": "2019-03-19"
}]
},
#edit
I add a javascript code. The function getTasks was displaying this json file in html site. So, maybe in here I should make a changes.
var todos = new Array();
var todo_index = 0;
window.onload = init;
function init() {
var submitButton = document.getElementById("submit");
submitButton.onclick = getFormData;
getTodoData();
}
function getTodoData() {
function request(method, url, data=null) {
return new Promise((resolve, reject)=> {
const xhr = new XMLHttpRequest;
xhr.timeout = 2000;
//xhr.responseType = 'json';
xhr.onreadystatechange = (e) => {
if(xhr.readyState === 4){
xhr.status === 200 ? resolve(xhr.response) : reject(xhr.status)
}
}
xhr.ontimeout = () => reject('timeout');
xhr.open(method, url, true);
if(method.toString().toLowerCase() === 'get') {
xhr.send(data)
} else {
xhr.setRequestHeader('Accept','application/json');
xhr.setRequestHeader('Content-type', 'application/json');
xhr.send(data)
}
})
}
async function getTasks(){
const task = await request('GET', '/WebService/todo.json');
document.getElementById("todoList").innerHTML=task
}
getTasks()
}
function parseTodoItems(todoJSON) {
if (todoJSON == null || todoJSON.trim() == "") {
return;
}
var todoArray = JSON.parse(todoJSON);
if (todoArray.length == 0) {
console.log("Error: Array is empty!");
return;
}
for (var i = 0; i < todoArray.length; i++) {
var todoItem = todoArray[i];
todos.push(todoItem);
}
}
function checkInputText(value, msg) {
if (value == null || value == "") {
alert(msg);
return true;
}
return false;
}
function Todo(index, part) {
this.index = index;
this.part = part;
}
function addTodosToPage() {
var table = document.getElementById("todoList");
var tr = document.createElement("tr");
var index = document.getElementById('index').value;
var part = document.getElementById('part').value;
tr.innerHTML = "<td>" + index + "</td><td>" + part + "</td>";
table.appendChild(tr);
todo_index++;
tr.id = "todo-" + todo_index;
var index = document.getElementById('index').value;
var part = document.getElementById('part').value;
tr.innerHTML = "\
<td><input name='select-row' type='checkbox' value='" + todo_index + "'></td>\
<td>" + index + "</td>\
<td>" + part + "</td>\
<td><button onclick='removeTodo(" + todo_index + ");'>x</button></td>";
table.appendChild(tr);
}
function getFormData() {
var index = document.getElementById("index").value;
var part = document.getElementById("part").value;
console.log("Index: " + index + " part: "+ part);
var todoItem = new Todo(index, part);
todos.push(todoItem);
addTodosToPage(todoItem);
saveTodoData();
}
function checkInputText(value, msg) {
if (value == null || value == "") {
alert(msg);
return true;
}
return false;
}
function saveTodoData() {
var todoJSON = JSON.stringify(todos);
var request = new XMLHttpRequest();
var URL = "save.php?data=" + encodeURI(todoJSON);
request.open("GET", URL);
request.setRequestHeader("Content-Type",
"text/plain;charset=UTF-8");
request.send();
}
function removeTodo(index) {
var row = document.getElementById('todo-' + index);
if (row) {
row.parentNode.removeChild(row);
}
todo_index--;
}
function toggleSelection(checkbox) {
var rowsToSelect = document.querySelectorAll('input[name=select-row]');
for (var i = 0; i < rowsToSelect.length; i++) {
rowsToSelect[i].checked = checkbox.checked;
}
}
function removeSelectedTodos() {
var rowsToRemove = document.querySelectorAll('input[name=select-row]:checked');
for (var i = 0; i < rowsToRemove.length; i++) {
removeTodo(rowsToRemove[i].value);
}
}
function setselection(){
var project = document.getElementById('todoList').value;
document.cookie = 'todotabel=' + project;
}
function getselection(){
var name = 'todotabela=';
var x = document.cookie.split(';');
var i = 0, c = 0;
for(i = 0; i < x.length; i++) {
c = x[i];
while (c.charAt(0) === ' ') {
c = c.substring(1);
}
if (c.indexOf(selectedProject) === 0) {
return c.substring(name.length, c.length);
}
} return '';
}
function remove() {
var arr = [];
var obj = {
'index': document.getElementById("index").value
};
for (var i = arr.length - 1; i >= 0; i--) {
if (arr[i]['index'] === obj['index']) {
arr.splice(i, 1);
}
}
localStorage.removeItem("user", JSON.stringify(arr));
}
function appendLocalStorage(keys, data) {
var old = localStorage.getItem(index);
if (old === null) old = "";
localStorage.setItem(index, old + data);
}
function addTo() {
var arr = [];
var obj = {
'index': document.getElementById("index").value,
'part': document.getElementById("part").value,
};
if (!arr.some(e => e['index'] == obj['index'])) {
arr.push(obj);
} else {
arr[arr.map((e, i) => [i, e]).filter(e => e[1]['index'] == obj['index'])[0][0]] = obj;
}
appendLocalStorage("user", JSON.stringify(arr));
alert(localStorage.getItem("user"));
}
This data is saved from input file by php and javascript function
How can I delete one of objects in array? Etc. I want to delete object with index:2 And I need delete this by button in html. How can I do this?
My php file:
$unsafe_json = json_decode($_GET["data"], true);
if (!is_array($unsafe_json)) {
die('Error save');
}
$safe_json = ['data' => []];
$values = ['index', 'part', 'dueDate'];
foreach ($unsafe_json as $unsafe_todo) {
$safe_todo = [];
foreach ($values as $value) {
if (isset($unsafe_todo[$value]) && is_string($unsafe_todo[$value])) {
$safe_todo[$value] = filter_var($unsafe_todo[$value], FILTER_SANITIZE_STRING);
} else {
$safe_todo[$value] = false;
}
}
* /
$safe_json['data'][] = $safe_todo;
}
$file = fopen("todo.json", "a");
fwrite($file, '' . json_encode($safe_json) . ',');
fclose($file);
$data = file_get_contents('todo.json');
i think what you are looking for is
unset($OBJECT['INDEX']);
you can iterate through your JSON, and when you match you condition you can call PHP's unset() method to remove the index
*Update
Code sample to remove with php
$json_decoded = json_decode($json_encoded, true);
foreach ($json_decoded as $i => $object)
if ($object['data']['index'] == 2)
unset($json_decoded[$i]);
I created a script in PHP to find a palindrome, but when I try to do the same in JavaScript, then it is not working as expected. It's not just a matter of checking if the string that is reversed matches, but any order of the string has to be checked as well.
In other words, "mom" should return as true, "mmo" should return as true, "omm" should return as true, etc..., which is what the PHP script does, but the JS script below doesn't even work for the first iteration for the string "mom"
The following is the PHP script:
<?php
function is_palindrom($str) {
$str_array = str_split($str);
$count = array();
foreach ($str_array as $key) {
if(isset($count[$key])) {
$count[$key]++;
} else {
$count[$key] = 1;
}
}
$odd_counter = 0;
foreach ($count as $key => $val) {
if(($val % 2) == 1) {
$odd_counter++;
}
}
return $odd_counter <= 1;
}
echo is_palindrom('mom') ? "true" : "false";
The following is what I have tried in JS:
var count = [];
var strArr = [];
var oddCounter = 0;
var foreach_1 = function(item, index) {
console.log("count[index]: " + count[index]);
if (typeof count[index] !== "undefined") {
count[index]++;
} else {
count[index] = 1;
}
};
var foreach_2 = function(item, index) {
console.log("item: " + item + " item % 2: " + eval(item % 2));
if (eval(item % 2) == 1) {
oddCounter++;
}
console.log("oddCounter: " + oddCounter);
return oddCounter <= 1;
};
var isPalindrom = function(str) {
strArr = str.split("");
console.log(strArr);
strArr.forEach(foreach_1);
console.log(count);
count.forEach(foreach_2);
};
I believe it is failing where I try to replicate isset in javascript, with the following code:
if (typeof count[index] !== "undefined") {
As a result, I have tried to write my own isset function, but still the same result, it is not working:
var isset = function(obj) {
if (typeof obj === "undefined" || obj === null) {
return false;
} else {
return true;
}
};
With the following function being called:
if (isset(count[index])) {
count[index]++;
} else {
count[index] = 1;
}
As usual, any help would be appreciated and thanks in advance
BTW, it's killing me that I cannot remember the word for several revisions or iterations of something - I know that it starts with "re"
My attempt:
let p1 = `No 'x' in Nixon.`
let p2 = `Was it a car or a cat I saw?`
let p3 = `A man, a plan, a canal, Panama!`
function is_palindrome (str) {
const normalize = str => str.replace(/[.,:;`'"!?\/#$%\^&\*{}=\-_~()\s]/g, '').toLowerCase()
const reverse = str => [...str].reverse().join('')
return normalize(str) === reverse(normalize(str))
? true
: false
}
console.log(is_palindrome(p1))
console.log(is_palindrome(p2))
console.log(is_palindrome(p3))
First, thank you for all the comments.
Second, I ran a var_dump on the count array in the PHP file and this was the result:
array (size=2)
'm' => int 2
'o' => int 1
Which lead me to understand that count in js has to be an object for this work and I would have to create indexes of the object, depending on the string entered.
One thing lead to another and a complete re-write, but it works, along with a spell checker - see link at the bottom for complete code:
var count = {};
var strArr = [];
var oddCounter = 0;
var objKeys = [];
var splitString;
var reverseArray;
var joinArray;
var url = "test-spelling.php";
var someRes = "";
var mForN = function(obj, strArr) {
for (var y = 0; y < strArr.length; y++) {
// console.log("obj[strArr[" + y + "]]: " + obj[strArr[y]]);
if (isset(obj[strArr[y]])) {
obj[strArr[y]]++;
} else {
obj[strArr[y]] = 1;
}
}
return obj;
};
var mForN_2 = function(obj, objKeys) {
for (var z = 0; z < objKeys.length; z++) {
/* console.log(
"obj[objKeys[z]]: " +
obj[objKeys[z]] +
" obj[objKeys[z]] % 2: " +
eval(obj[objKeys[z]] % 2)
); */
if (eval(obj[objKeys[z]] % 2) == 1) {
oddCounter++;
}
// console.log("oddCounter: " + oddCounter);
}
return oddCounter <= 1;
};
var isset = function(obj) {
if (typeof obj === "undefined" || obj === null) {
return false;
} else {
return true;
}
};
var isPalindrom = function(str) {
// reverse original string
splitString = str.split("");
reverseArray = splitString.reverse();
joinArray = reverseArray.join("");
var checking = checkSpellingOfStr(str);
if (str == joinArray) {
strArr = str.split("");
// console.log("strArr: " + strArr);
objKeys = makeObjKeys(count, strArr);
// console.log("filled count before mForN: " + JSON.stringify(count));
// create array of keys in the count object
objKeys = Object.keys(count);
// console.log("objKeys: " + objKeys);
count = mForN(count, strArr);
// console.log("count after mForN: " + JSON.stringify(count));
return mForN_2(count, objKeys);
} else {
return 0;
}
};
var makeObjKeys = function(obj, arr) {
for (var x = 0; x < arr.length; x++) {
obj[arr[x]] = null;
}
return obj;
};
var checkSpellingOfStr = function(someStr) {
var formData = {
someWord: someStr
};
$.ajax({
type: "GET",
url: url,
data: formData,
success: function(result) {
if (!$.trim(result)) {
} else {
console.log(result);
$("#checkSpelling").html(result);
}
}
});
};
Start everything with the following call:
isPalindrom("mom") ? demoP.innerHTML = "is pal" : demoP.innerHTML = "is not pal";
In my example, I have a form and I listen for a button click as follows:
var palindromeTxt = document.getElementById("palindromeTxt").value;
var btn = document.getElementById("button");
btn.addEventListener("click", function (event) {
isPalindrom(palindromeTxt) ? demoP.innerHTML = "is pal" : demoP.innerHTML = "is not pal";
});
The following is the php for spell check:
<?php
error_reporting(E_ALL);
ini_set('display_errors', 1);
if(!empty($_REQUEST['someWord']))
{
$someWord = $_REQUEST['someWord'];
}
$pspell_link = pspell_new("en");
if (pspell_check($pspell_link, $someWord)) {
echo trim($someWord) . " is a recognized word in the English language";
} else {
echo "Your word is either misspelled or that is not a recognized word";
}
You will need pspell installed on your server, as well as adding extension=pspell.so to your php.ini
This is what I did, to get it running locally on my mac:
cd /Users/username/Downloads/php-5.6.2/ext/pspell
/usr/local/bin/phpize
./configure --with-php-config=/usr/local/php5-5.6.2-20141102-094039/bin/php-config --with-pspell=/opt/local/
make
cp ./modules/* /usr/local/php5-5.6.2-20141102-094039/lib/php/extensions/no-debug-non-zts-20131226
sudo apachectl restart
check your phpinfo file and you should see the following:
pspell
PSpell Support enabled
Live example
We create ASP.NET MVC5 project with AngularJS and WebApi 2. In some views we need paging for EntityList. For this purpose we write WebApi action as follows:
[HttpGet]
[Route("GetAll/{pageSize:int}/{pageNumber:int}/{caseType?}/{caseDate?}/{caseNumber?}/{entryDate?}/{entryNumber?}/{seenForm?}/{levelOfAccess?}/{tagWords?}/{senderOrganization?}/{senderPerson?}")]
[AgPermission(System.Security.Permissions.SecurityAction.Demand)]
//[Authorize(Roles = "Katiblik")]
public ObjectWrapperWithNameOfSet GetAll(int pageSize, int pageNumber,int? caseType = null,string caseDate = null,string caseNumber = null,string entryDate = null,string entryNumber = null,SeenForm? seenForm = null,LevelOfAccess? levelOfAccess = null,string tagWords = null,int? senderOrganization = null, int? senderPerson = null)
{
var caseQuery = service.List().List;
if (caseType != null)
{
caseQuery = caseQuery.Where(#case => #case.CaseType.Id == caseType).ToList();
}
if (caseDate != "null")
{
caseQuery = caseQuery.Where(#case => #case.CaseDate == DateTime.ParseExact(caseDate, "ddMMyyyy", null)).ToList();
}
if (caseNumber != "null")
{
caseQuery = caseQuery.Where(#case => #case.CaseNumber == caseNumber).ToList();
}
if (entryDate != "null")
{
caseQuery = caseQuery.Where(#case => #case.EntryDate == DateTime.ParseExact(entryDate, "ddMMyyyy", null)).ToList();
}
if (entryNumber != "null")
{
caseQuery = caseQuery.Where(#case => #case.EntryNumber == entryNumber).ToList();
}
if (seenForm != null)
{
caseQuery = caseQuery.Where(#case => #case.SeenForm == seenForm).ToList();
}
if (levelOfAccess != null)
{
caseQuery = caseQuery.Where(#case => #case.LevelOfAccess == levelOfAccess).ToList();
}
if (tagWords != "null")
{
caseQuery = caseQuery.Where(#case => #case.TagedWords.Contains(tagWords)).ToList();
}
if (senderOrganization != null)
{
caseQuery = caseQuery.Where(#case => #case.SenderOrganization.Id == senderOrganization).ToList();
}
if (senderPerson != null)
{
caseQuery = caseQuery.Where(#case => #case.SenderPerson.Id == senderPerson).ToList();
}
var totalCount = caseQuery.Count();
var totalPages = Math.Ceiling((double)totalCount / pageSize);
var cases = caseQuery.Skip((pageNumber - 1) * pageSize)
.Take(pageSize)
.ToList();
var result = new
{
TotalCount = totalCount,
totalPages = totalPages,
Cases = cases
};
return new ObjectWrapperWithNameOfSet("list", result);
}
But it seemed not advanced and not clearly understanted method for Paging in WebApi2. We have many data for the case entity and we must create searching for every column of table.
So my question is
How to create Advanced AngularJS paging with WEB API2?
I upgrade magento from 1.8.1 to 1.9.0, and I have a problem with one js file:
TypeError: $(...) is null
$('product_addtocart_form').getElements().each(function(el) {
simple_product_pricing.js (line 1131, col 5)
I think this file is related to the Ayasoftware_SimpleProductPricing, maybe someone can help me to solve this. Before upgrade in 1.8.1 version everything was fine, in 1.9.0 version I have this error.
I will add here the entire js:
/*
Some of these override earlier varien/product.js methods, therefore
varien/product.js must have been included prior to this file.
some of these functions were initially written by Matt Dean ( http://organicinternet.co.uk/ )
*/
Product.Config.prototype.getMatchingSimpleProduct = function(){
var inScopeProductIds = this.getInScopeProductIds();
if ((typeof inScopeProductIds != 'undefined') && (inScopeProductIds.length == 1)) {
return inScopeProductIds[0];
}
return false;
};
/*
Find products which are within consideration based on user's selection of
config options so far
Returns a normal array containing product ids
allowedProducts is a normal numeric array containing product ids.
childProducts is a hash keyed on product id
optionalAllowedProducts lets you pass a set of products to restrict by,
in addition to just using the ones already selected by the user
*/
Product.Config.prototype.getInScopeProductIds = function(optionalAllowedProducts) {
var childProducts = this.config.childProducts;
var allowedProducts = [];
if ((typeof optionalAllowedProducts != 'undefined') && (optionalAllowedProducts.length > 0)) {
allowedProducts = optionalAllowedProducts;
}
for(var s=0, len=this.settings.length-1; s<=len; s++) {
if (this.settings[s].selectedIndex <= 0){
break;
}
var selected = this.settings[s].options[this.settings[s].selectedIndex];
if (s==0 && allowedProducts.length == 0){
allowedProducts = selected.config.allowedProducts;
} else {
allowedProducts = allowedProducts.intersect(selected.config.allowedProducts).uniq();
}
}
//If we can't find any products (because nothing's been selected most likely)
//then just use all product ids.
if ((typeof allowedProducts == 'undefined') || (allowedProducts.length == 0)) {
productIds = Object.keys(childProducts);
} else {
productIds = allowedProducts;
}
return productIds;
};
Product.Config.prototype.getProductIdOfCheapestProductInScope = function(priceType, optionalAllowedProducts) {
var childProducts = this.config.childProducts;
var productIds = this.getInScopeProductIds(optionalAllowedProducts);
var minPrice = Infinity;
var lowestPricedProdId = false;
//Get lowest price from product ids.
for (var x=0, len=productIds.length; x<len; ++x) {
var thisPrice = Number(childProducts[productIds[x]][priceType]);
if (thisPrice < minPrice) {
minPrice = thisPrice;
lowestPricedProdId = productIds[x];
}
}
return lowestPricedProdId;
};
Product.Config.prototype.getProductIdOfMostExpensiveProductInScope = function(priceType, optionalAllowedProducts) {
var childProducts = this.config.childProducts;
var productIds = this.getInScopeProductIds(optionalAllowedProducts);
var maxPrice = 0;
var highestPricedProdId = false;
//Get highest price from product ids.
for (var x=0, len=productIds.length; x<len; ++x) {
var thisPrice = Number(childProducts[productIds[x]][priceType]);
if (thisPrice >= maxPrice) {
maxPrice = thisPrice;
highestPricedProdId = productIds[x];
}
}
return highestPricedProdId;
};
Product.OptionsPrice.prototype.updateSpecialPriceDisplay = function(price, finalPrice) {
var prodForm = $('product_addtocart_form');
jQuery('p.msg').hide();
jQuery('div.price-box').show();
var specialPriceBox = prodForm.select('p.special-price');
var oldPricePriceBox = prodForm.select('p.old-price, p.was-old-price');
var magentopriceLabel = prodForm.select('span.price-label');
if (price == finalPrice) {
//specialPriceBox.each(function(x) {x.hide();});
magentopriceLabel.each(function(x) {x.hide();});
oldPricePriceBox.each(function(x) { x.hide();
// x.removeClassName('old-price');
// x.addClassName('was-old-price');
});
jQuery('.product-shop').removeClass('sale-product') ;
}else{
specialPriceBox.each(function(x) {x.show();});
magentopriceLabel.each(function(x) {x.show();});
oldPricePriceBox.each(function(x) { x.show();
x.removeClassName('was-old-price');
x.addClassName('old-price');
});
jQuery('.product-shop').addClass('sale-product') ;
}
};
//This triggers reload of price and other elements that can change
//once all options are selected
Product.Config.prototype.reloadPrice = function() {
var childProductId = this.getMatchingSimpleProduct();
var childProducts = this.config.childProducts;
var usingZoomer = false;
if(this.config.imageZoomer){
usingZoomer = true;
}
if(childProductId){
var price = childProducts[childProductId]["price"];
var finalPrice = childProducts[childProductId]["finalPrice"];
optionsPrice.productPrice = finalPrice;
optionsPrice.productOldPrice = price;
optionsPrice.reload();
optionsPrice.reloadPriceLabels(true);
optionsPrice.updateSpecialPriceDisplay(price, finalPrice);
if(this.config.updateShortDescription) {
this.updateProductShortDescription(childProductId);
}
if(this.config.updateDescription) {
this.updateProductDescription(childProductId);
}
if(this.config.updateProductName) {
this.updateProductName(childProductId);
}
if(this.config.customStockDisplay) {
this.updateProductAvailability(childProductId);
}
this.showTierPricingBlock(childProductId, this.config.productId);
if (usingZoomer) {
this.showFullImageDiv(childProductId, this.config.productId);
} else {
if(this.config.updateproductimage) {
this.updateProductImage(childProductId);
}
}
} else {
var cheapestPid = this.getProductIdOfCheapestProductInScope("finalPrice");
var price = childProducts[cheapestPid]["price"];
var finalPrice = childProducts[cheapestPid]["finalPrice"];
optionsPrice.productPrice = finalPrice;
optionsPrice.productOldPrice = price;
optionsPrice.reload();
optionsPrice.reloadPriceLabels(false);
if(this.config.updateProductName) {
this.updateProductName(false);
}
if(this.config.updateShortDescription) {
this.updateProductShortDescription(false);
}
if(this.config.updateDescription) {
this.updateProductDescription(false);
}
if(this.config.customStockDisplay) {
this.updateProductAvailability(false);
}
optionsPrice.updateSpecialPriceDisplay(price, finalPrice);
this.showTierPricingBlock(false);
this.showCustomOptionsBlock(false, false);
if (usingZoomer) {
this.showFullImageDiv(false, false);
} else {
if(this.config.updateproductimage) {
this.updateProductImage(false);
}
}
}
};
Product.Config.prototype.updateProductImage = function(productId) {
var imageUrl = this.config.imageUrl;
if(productId && this.config.childProducts[productId].imageUrl) {
imageUrl = this.config.childProducts[productId].imageUrl;
}
if (!imageUrl) {
return;
}
if($('image')) {
$('image').src = imageUrl;
} else {
$$('#product_addtocart_form p.product-image img').each(function(el) {
var dims = el.getDimensions();
el.src = imageUrl;
el.width = dims.width;
el.height = dims.height;
});
}
};
Product.Config.prototype.updateProductName = function(productId) {
var productName = this.config.productName;
if (productId && this.config.ProductNames[productId].ProductName) {
productName = this.config.ProductNames[productId].ProductName;
}
$$('#product_addtocart_form div.product-name h1').each(function(el) {
el.innerHTML = productName;
});
var productSku = this.config.sku ;
if (productId && this.config.childProducts[productId].sku) {
productSku = this.config.childProducts[productId].sku ;
}
jQuery('.sku span').text(productSku) ;
var productDelivery = this.config.delivery;
if (productId && this.config.childProducts[productId].delivery) {
productDelivery = this.config.childProducts[productId].delivery ;
}
jQuery('.delivery-info').html(productDelivery) ;
var productReturns = this.config.returns;
if (productId && this.config.childProducts[productId].returns) {
productReturns = this.config.childProducts[productId].returns ;
}
jQuery('.returns-info').html(productReturns) ;
var productDownloads = this.config.downloads;
if (productId && this.config.childProducts[productId].downloads) {
productDownloads = this.config.childProducts[productId].downloads;
}
if (productDownloads) jQuery('.downloads-info').html(productDownloads) ;
else jQuery('.downloads-info').html('There are no downloads for this product') ;
var productAttribs = this.config.attributesTable;
if (productId && this.config.childProducts[productId].attributesTable) {
productAttribs = this.config.childProducts[productId].attributesTable ;
}
jQuery('.attribs-info').html(productAttribs) ;
decorateTable('product-attribute-specs-table') ;
if (productId && this.config.childProducts[productId].isNew) {
jQuery('.product-image .new-label').show() ;
} else {
jQuery('.product-image .new-label').hide() ;
}
if (productId && this.config.childProducts[productId].isOnSale) {
jQuery('.product-image .sale-label').show() ;
} else {
jQuery('.product-image .sale-label').hide() ;
}
if (productId) jQuery('input[name="pid"]').val(productId) ;
};
Product.Config.prototype.updateProductAvailability = function(productId) {
var stockInfo = this.config.stockInfo;
var is_in_stock = false;
var stockLabel = '';
if (productId && stockInfo[productId]["stockLabel"]) {
stockLabel = stockInfo[productId]["stockLabel"];
stockQty = stockInfo[productId]["stockQty"];
is_in_stock = stockInfo[productId]["is_in_stock"];
}
$$('#product_addtocart_form p.availability span').each(function(el) {
if(is_in_stock) {
$$('#product_addtocart_form p.availability').each(function(es) {
es.removeClassName('availability out-of-stock');
es.addClassName('availability in-stock');
});
el.innerHTML = /*stockQty + ' ' + */stockLabel;
} else {
$$('#product_addtocart_form p.availability').each(function(ef) {
ef.removeClassName('availability in-stock');
ef.addClassName('availability out-of-stock');
});
el.innerHTML = stockLabel;
}
});
};
Product.Config.prototype.updateProductShortDescription = function(productId) {
var shortDescription = this.config.shortDescription;
if (productId && this.config.shortDescriptions[productId].shortDescription) {
shortDescription = this.config.shortDescriptions[productId].shortDescription;
}
$$('#product_addtocart_form div.short-description div.std').each(function(el) {
el.innerHTML = shortDescription;
});
};
Product.Config.prototype.updateProductDescription = function(productId) {
var description = this.config.description;
if (productId && this.config.Descriptions[productId].Description) {
description = this.config.Descriptions[productId].Description;
}
$$('#product_tabs_description_tabbed_contents div.std').each(function(el) {
el.innerHTML = description;
});
};
Product.Config.prototype.updateProductAttributes = function(productId) {
var productAttributes = this.config.productAttributes;
if (productId && this.config.childProducts[productId].productAttributes) {
productAttributes = this.config.childProducts[productId].productAttributes;
}
//If config product doesn't already have an additional information section,
//it won't be shown for associated product either. It's too hard to work out
//where to place it given that different themes use very different html here
console.log(productAttributes) ;
$$('div.product-collateral div.attribs-info').each(function(el) {
el.innerHTML = productAttributes;
decorateTable('product-attribute-specs-table');
});
};
Product.Config.prototype.showCustomOptionsBlock = function(productId, parentId) {
var coUrl = this.config.ajaxBaseUrl + "co/?id=" + productId + '&pid=' + parentId;
var prodForm = $('product_addtocart_form');
if ($('SCPcustomOptionsDiv')==null) {
return;
}
Effect.Fade('SCPcustomOptionsDiv', { duration: 0.5, from: 1, to: 0.5 });
if(productId) {
//Uncomment the line below if you want an ajax loader to appear while any custom
//options are being loaded.
//$$('span.scp-please-wait').each(function(el) {el.show()});
//prodForm.getElements().each(function(el) {el.disable()});
new Ajax.Updater('SCPcustomOptionsDiv', coUrl, {
method: 'get',
evalScripts: true,
onComplete: function() {
$$('span.scp-please-wait').each(function(el) {el.hide()});
Effect.Fade('SCPcustomOptionsDiv', { duration: 0.5, from: 0.5, to: 1 });
//prodForm.getElements().each(function(el) {el.enable()});
}
});
} else {
$('SCPcustomOptionsDiv').innerHTML = '';
try{window.opConfig = new Product.Options([]);} catch(e){}
}
};
Product.OptionsPrice.prototype.reloadPriceLabels = function(productPriceIsKnown) {
var priceFromLabel = '';
var prodForm = $('product_addtocart_form');
if (!productPriceIsKnown && typeof spConfig != "undefined") {
priceFromLabel = spConfig.config.priceFromLabel;
}
var priceSpanId = 'configurable-price-from-' + this.productId;
var duplicatePriceSpanId = priceSpanId + this.duplicateIdSuffix;
if($(priceSpanId) && $(priceSpanId).select('span.configurable-price-from-label'))
$(priceSpanId).select('span.configurable-price-from-label').each(function(label) {
label.innerHTML = priceFromLabel;
});
if ($(duplicatePriceSpanId) && $(duplicatePriceSpanId).select('span.configurable-price-from-label')) {
$(duplicatePriceSpanId).select('span.configurable-price-from-label').each(function(label) {
label.innerHTML = priceFromLabel;
});
}
};
//SCP: Forces the 'next' element to have it's optionLabels reloaded too
Product.Config.prototype.configureElement = function(element) {
this.reloadOptionLabels(element);
if(element.value){
this.state[element.config.id] = element.value;
if(element.nextSetting){
element.nextSetting.disabled = false;
this.fillSelect(element.nextSetting);
this.reloadOptionLabels(element.nextSetting);
this.resetChildren(element.nextSetting);
}
}
else {
this.resetChildren(element);
}
this.reloadPrice();
};
//SCP: Changed logic to use absolute price ranges rather than price differentials
Product.Config.prototype.reloadOptionLabels = function(element){
var selectedPrice;
var childProducts = this.config.childProducts;
var stockInfo = this.config.stockInfo;
//Don't update elements that have a selected option
if(element.options[element.selectedIndex].config){
return;
}
for(var i=0;i<element.options.length;i++){
if(element.options[i].config){
var cheapestPid = this.getProductIdOfCheapestProductInScope("finalPrice", element.options[i].config.allowedProducts);
var mostExpensivePid = this.getProductIdOfMostExpensiveProductInScope("finalPrice", element.options[i].config.allowedProducts);
var cheapestFinalPrice = childProducts[cheapestPid]["finalPrice"];
var mostExpensiveFinalPrice = childProducts[mostExpensivePid]["finalPrice"];
var stock = '';
if(cheapestPid == mostExpensivePid ){
if(stockInfo[cheapestPid]["stockLabel"] != '') {
stock = '( ' +stockInfo[cheapestPid]["stockLabel"] + ' )';
}
}
if (this.config.showOutOfStock){
if(this.config.disable_out_of_stock_option ) {
if(!stockInfo[cheapestPid]["is_in_stock"] ) {
if(cheapestPid == mostExpensivePid ){
element.options[i].disabled=true;
var stock = '( ' +stockInfo[cheapestPid]["stockLabel"] + ' )';
}
}
}
}
var tierpricing = childProducts[mostExpensivePid]["tierpricing"];
element.options[i].text = this.getOptionLabel(element.options[i].config, cheapestFinalPrice, mostExpensiveFinalPrice, stock , tierpricing);
}
}
};
Product.Config.prototype.showTierPricingBlock = function(productId, parentId) {
var coUrl = this.config.ajaxBaseUrl + "co/?id=" + productId + '&pid=' + parentId;
var prodForm = $('product_addtocart_form');
if(productId) {
new Ajax.Updater('sppTierPricingDiv', coUrl, {
method: 'get',
evalScripts: true,
onComplete: function() {
$$('span.scp-please-wait').each(function(el) {el.hide()});
}
});
} else {
$('sppTierPricingDiv').innerHTML = '';
}
};
//SCP: Changed label formatting to show absolute price ranges rather than price differentials
Product.Config.prototype.getOptionLabel = function(option, lowPrice, highPrice, stock, tierpricing){
var str = option.label;
if(tierpricing > 0 && tierpricing < lowPrice) {
var tierpricinglowestprice = ': As low as (' + this.formatPrice(tierpricing,false) + ')';
} else {
var tierpricinglowestprice = '';
}
if (!this.config.showPriceRangesInOptions) {
return str;
}
if (!this.config.showOutOfStock){
stock = '';
}
lowPrices = this.getTaxPrices(lowPrice);
highPrices = this.getTaxPrices(highPrice);
if (this.config.hideprices) {
if (this.config.showOutOfStock){
return str + ' ' + stock + ' ';
} else {
return str;
}
}
var to = ' ' + this.config.rangeToLabel + ' ';
var separator = ': ( ';
if(lowPrice && highPrice){
if (this.config.showfromprice) {
this.config.priceFromLabel = this.config.priceFromLabel; //'From: ';
}
if (lowPrice != highPrice) {
if (this.taxConfig.showBothPrices) {
str+= separator + this.formatPrice(lowPrices[2], false) + ' (' + this.formatPrice(lowPrices[1], false) + ' ' + this.taxConfig.inclTaxTitle.replace('Tax','VAT') + ')';
str+= to + this.formatPrice(highPrices[2], false) + ' (' + this.formatPrice(highPrices[1], false) + ' ' + this.taxConfig.inclTaxTitle.replace('Tax','VAT') + ')';
str += " ) ";
} else {
str+= separator + this.formatPrice(lowPrices[0], false);
str+= to + this.formatPrice(highPrices[0], false);
str += " ) ";
}
} else {
if (this.taxConfig.showBothPrices) {
str+= separator + this.formatPrice(lowPrices[2], false) + ' (' + this.formatPrice(lowPrices[1], false) + ' ' + this.taxConfig.inclTaxTitle.replace('Tax','VAT') + ')';
str += " ) ";
str += stock;
str += tierpricinglowestprice;
} else {
if(tierpricing == 0 ) {
str+= separator + this.formatPrice(lowPrices[0], false);
str += " ) ";
}
str += tierpricinglowestprice;
str += ' ' + stock;
}
}
}
return str;
};
//SCP: Refactored price calculations into separate function
Product.Config.prototype.getTaxPrices = function(price) {
var price = parseFloat(price);
if (this.taxConfig.includeTax) {
var tax = price / (100 + this.taxConfig.defaultTax) * this.taxConfig.defaultTax;
var excl = price - tax;
var incl = excl*(1+(this.taxConfig.currentTax/100));
} else {
var tax = price * (this.taxConfig.currentTax / 100);
var excl = price;
var incl = excl + tax;
}
if (this.taxConfig.showIncludeTax || this.taxConfig.showBothPrices) {
price = incl;
} else {
price = excl;
}
return [price, incl, excl];
};
//SCP: Forces price labels to be updated on load
//so that first select shows ranges from the start
document.observe("dom:loaded", function() {
//Really only needs to be the first element that has configureElement set on it,
//rather than all.
if (typeof opConfig != "undefined") {
spConfig.reloadPrice();
}
$('product_addtocart_form').getElements().each(function(el) {
if(el.type == 'select-one') {
if(el.options && (el.options.length > 1)) {
el.options[0].selected = true;
spConfig.reloadOptionLabels(el);
}
}
});
});
Thank you
The version 1.5.11 is not compatible w/ Magento 1.9 according to the extension version on Magento connect. Please obtain the newest version of the extension and/or ask the creator to give you support. As far as I can see 1.9 support is support with 1.11.6, released 11th March 2015. The infos on their homepage and Magento connect are different - not good. On the homepage it says Works with Magento 1.9.0.X . tested 15 May 2014.