5 | LINQ to JavaScript - Samples Unit Tests
6 |
7 |
8 |
9 |
10 |
LINQ to JavaScript - Test Samples
11 |
12 | JSLINQ v
13 |
14 |
This page performs automated unit tests on each of the JSLINQ Samples. Just click "Run Test" to start the Unit Tests. The results will be displayed below once they are finished.
15 | Test Results:
16 |
17 |
18 | Back...
19 |
20 |
23 |
24 |
--------------------------------------------------------------------------------
/Nuget/package/jslinq.nuspec:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 | jslinq
5 | LINQ to JavaScript
6 | 2.30
7 | Chris Pietschmann
8 | Chris Pietschmann
9 | https://github.com/crpietschmann/jslinq/blob/master/LICENSE
10 | https://github.com/crpietschmann/jslinq
11 | false
12 | LINQ to JavaScript (JSLINQ) is an implementation of LINQ to Objects for JavaScript. It is simple to use and gives much needed power and flexibility to performing LINQ style queries agains traditional JavaScript Arrays. If you are using an Array, you can use LINQ to JavaScript to step up your game.
13 | https://github.com/crpietschmann/jslinq/blob/master/Website/ReadMe.txt
14 | Copyright (c) 2013-2023 Chris Pietschmann
15 | javascript js linq array objects
16 |
17 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) 2017-2023 Chris Pietschmann
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/Website/Examples/Array/CountSetOfWords.htm:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | JSLINQ Example: Count Occurrences of a Set of Words within a String
6 |
7 |
21 |
22 |
23 |
JSLINQ Example: Count Occurrences of a Set of Words within a String
24 |
This examples shows how to count the number of times each word within a set of words occurs within a string.
25 |
26 | Words to find: (seperate by a space)
27 | String to check:
28 |
29 |
30 |
31 |
32 |
33 | Back...
34 |
35 |
36 |
--------------------------------------------------------------------------------
/Website/Examples/Array/CountWordOccurrences.htm:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | JSLINQ Example: Count Occurrences of a Word in a String
6 |
7 |
24 |
25 |
26 |
JSLINQ Example: Count Occurrences of a Word in a String
27 |
This examples shows how to count the number of time a specific words occurs within a string.
28 |
29 | Word to find:
30 | String to check:
31 |
32 |
33 |
34 |
JSLINQ Usage Examples - These are some usage examples that demonstrate some of the simple and more complex ways that JSLINQ can be used to manipulate data.
69 |
70 |
71 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # LINQ to JavaScript
2 |
3 | LINQ to JavaScript (`JSLINQ`) is LINQ to Objects for JavaScript arrays, and adds power and flexibility of LINQ style queries to traditional JavaScript code.
4 |
5 | ## What is LINQ to JavaScript?
6 |
7 | LINQ to JavaScript (JSLINQ for short) is an implementation of LINQ to Objects implemented in JavaScript. It is built using a set of extension methods built on top of the JavaScript Array object. If you are using Arrays then you can use JSLINQ; it's that simple!
8 |
9 | ## Nuget Package
10 |
11 | [http://nuget.org/packages/jslinq](http://nuget.org/packages/jslinq)
12 |
13 | 
14 |
15 | ## Example Usage
16 |
17 | If you don't know what LINQ it's a feature set in the .NET development framework that allows more SQL-like querying of any kind of data. In the case of `JSLINQ` / LINQ to JavaScript, it provides the ability to query against Arrays.
18 |
19 | var myList = [
20 | {FirstName:"Chris",LastName:"Pearson"},
21 | {FirstName:"Kate",LastName:"Johnson"},
22 | {FirstName:"Josh",LastName:"Sutherland"},
23 | {FirstName:"John",LastName:"Ronald"},
24 | {FirstName:"Steve",LastName:"Pinkerton"}
25 | ];
26 |
27 | var exampleArray = JSLINQ(myList)
28 | .Where((item) => item.FirstName == "Chris")
29 | .OrderBy((item) => item.FirstName)
30 | .Select((item) => item.FirstName);
31 |
32 | ## Using LINQ to JavaScript
33 |
34 | We will use this Array for the following examples:
35 |
36 | var myList = [
37 | {FirstName:"Chris",LastName:"Pearson"},
38 | {FirstName:"Kate",LastName:"Johnson"},
39 | {FirstName:"Josh",LastName:"Sutherland"},
40 | {FirstName:"John",LastName:"Ronald"},
41 | {FirstName:"Steve",LastName:"Pinkerton"}
42 | ];
43 |
44 | **Create an Instance of the JSLINQ object with your data**
45 |
46 | You need to create a new JSLINQ object and pass it the javascript array of data that you will be querying.
47 |
48 | var example = JSLINQ(myList);
49 |
50 | **Using the Where operator to specify query criteria**
51 |
52 | In this case, we're getting all items in the Array that have FirstName property set to Chris.
53 |
54 | var whereExample1 = JSLINQ(myList).
55 | Where(function(item){ return item.FirstName == "Chris"; });
56 |
57 | **Using the Select operator to specify which data to return**
58 |
59 | In this case, we're going to return only the FirstName property of each item in the Array.
60 |
61 | var selectTest2 = JSLINQ(myList).
62 | Select(function(item){ return item.FirstName; });
63 |
64 | **Using the OrderBy operator to determine how to sort the order of the items in the Array**
65 |
66 | In this case, we're going to order them by the FirstName property.
67 |
68 | var sortTest1 = JSLINQ(myList)
69 | .OrderBy(function(item){ return item.FirstName; });
70 |
71 | ## Related Links
72 |
73 | [JSLinq Editor](http://secretgeek.net/JsLinq/)
74 |
75 | 2010/03/16: [LINQ for JavaScript: Using and Extending JSLINQ](http://www.gregshackles.com/2010/03/linq-for-javascript-using-and-extending-jslinq/)
76 |
77 | 2008/01/24: [LINQ to JavaScript (JSLINQ) Open Source Project Launched!](http://pietschsoft.com/post/2008/01/24/LINQ-to-JavaScript-%28JSLINQ%29-Open-Source-Project-Launched!.aspx)
78 |
--------------------------------------------------------------------------------
/JSLINQ.sln:
--------------------------------------------------------------------------------
1 |
2 | Microsoft Visual Studio Solution File, Format Version 12.00
3 | # Visual Studio Version 17
4 | VisualStudioVersion = 17.5.33424.131
5 | MinimumVisualStudioVersion = 10.0.40219.1
6 | Project("{E24C65DC-7377-472B-9ABA-BC803B73C61A}") = "Website", "Website\", "{397777F9-0620-4C99-B329-B09AB03D85F3}"
7 | ProjectSection(WebsiteProperties) = preProject
8 | SccProjectName = "SAK"
9 | SccAuxPath = "SAK"
10 | SccLocalPath = "SAK"
11 | SccProvider = "SAK"
12 | TargetFrameworkMoniker = ".NETFramework,Version%3Dv4.8"
13 | Debug.AspNetCompiler.VirtualPath = "/Website"
14 | Debug.AspNetCompiler.PhysicalPath = "Website\"
15 | Debug.AspNetCompiler.TargetPath = "PrecompiledWeb\Website\"
16 | Debug.AspNetCompiler.Updateable = "true"
17 | Debug.AspNetCompiler.ForceOverwrite = "true"
18 | Debug.AspNetCompiler.FixedNames = "false"
19 | Debug.AspNetCompiler.Debug = "True"
20 | Release.AspNetCompiler.VirtualPath = "/Website"
21 | Release.AspNetCompiler.PhysicalPath = "Website\"
22 | Release.AspNetCompiler.TargetPath = "PrecompiledWeb\Website\"
23 | Release.AspNetCompiler.Updateable = "true"
24 | Release.AspNetCompiler.ForceOverwrite = "true"
25 | Release.AspNetCompiler.FixedNames = "false"
26 | Release.AspNetCompiler.Debug = "False"
27 | VWDPort = "1560"
28 | SlnRelativePath = "Website\"
29 | DefaultWebSiteLanguage = "Visual C#"
30 | EndProjectSection
31 | EndProject
32 | Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Nuget", "Nuget", "{9CC0875D-29D0-447F-8231-E9F4D7F03C14}"
33 | ProjectSection(SolutionItems) = preProject
34 | build.bat = build.bat
35 | Nuget\jslinq.2.10.1.nupkg = Nuget\jslinq.2.10.1.nupkg
36 | Nuget\jslinq.2.10.nupkg = Nuget\jslinq.2.10.nupkg
37 | Nuget\NuGet.exe = Nuget\NuGet.exe
38 | EndProjectSection
39 | EndProject
40 | Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "package", "package", "{C9B10C36-5744-4D25-8BE8-1E993624D4DB}"
41 | ProjectSection(SolutionItems) = preProject
42 | Nuget\package\jslinq.nuspec = Nuget\package\jslinq.nuspec
43 | EndProjectSection
44 | EndProject
45 | Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Content", "Content", "{59D05196-6DEF-4FD2-95EF-E625094232BB}"
46 | EndProject
47 | Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Scripts", "Scripts", "{C4E3084D-1B0F-47F8-8CEE-8533E0E85EDD}"
48 | ProjectSection(SolutionItems) = preProject
49 | Nuget\package\Content\Scripts\JSLINQ-vsdoc.js = Nuget\package\Content\Scripts\JSLINQ-vsdoc.js
50 | Nuget\package\Content\Scripts\JSLINQ.js = Nuget\package\Content\Scripts\JSLINQ.js
51 | EndProjectSection
52 | EndProject
53 | Global
54 | GlobalSection(SolutionConfigurationPlatforms) = preSolution
55 | Debug|Any CPU = Debug|Any CPU
56 | EndGlobalSection
57 | GlobalSection(ProjectConfigurationPlatforms) = postSolution
58 | {397777F9-0620-4C99-B329-B09AB03D85F3}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
59 | {397777F9-0620-4C99-B329-B09AB03D85F3}.Debug|Any CPU.Build.0 = Debug|Any CPU
60 | EndGlobalSection
61 | GlobalSection(SolutionProperties) = preSolution
62 | HideSolutionNode = FALSE
63 | EndGlobalSection
64 | GlobalSection(NestedProjects) = preSolution
65 | {C9B10C36-5744-4D25-8BE8-1E993624D4DB} = {9CC0875D-29D0-447F-8231-E9F4D7F03C14}
66 | {59D05196-6DEF-4FD2-95EF-E625094232BB} = {C9B10C36-5744-4D25-8BE8-1E993624D4DB}
67 | {C4E3084D-1B0F-47F8-8CEE-8533E0E85EDD} = {59D05196-6DEF-4FD2-95EF-E625094232BB}
68 | EndGlobalSection
69 | GlobalSection(ExtensibilityGlobals) = postSolution
70 | SolutionGuid = {198ABC44-7984-4C66-A375-24F8807658F9}
71 | EndGlobalSection
72 | EndGlobal
73 |
--------------------------------------------------------------------------------
/Website/Examples/HtmlDomTable.htm:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | JSLINQ Example: Search HTML DOM Table
6 |
7 |
55 |
56 |
57 |
JSLINQ Example: Search HTML DOM Table
58 |
This example demonstrates using an HTML Table as the data source for the JSLINQ query, and then displaying the search results within another Table on the page.
59 |
60 |
Query Results
61 | First Name contains:
62 |
63 |
64 |
65 |
ID
66 |
FirstName
67 |
LastName
68 |
69 |
70 |
71 |
72 |
73 |
74 |
Source Data
75 |
76 |
77 |
78 |
ID
79 |
FirstName
80 |
LastName
81 |
82 |
83 |
84 |
85 |
1
86 |
Chris
87 |
Pearson
88 |
89 |
90 |
2
91 |
Kate
92 |
Johnson
93 |
94 |
95 |
3
96 |
Josh
97 |
Sutherland
98 |
99 |
100 |
4
101 |
John
102 |
Ronald
103 |
104 |
105 |
5
106 |
Steve
107 |
Pinkerton
108 |
109 |
110 |
6
111 |
Katie
112 |
Zimmerman
113 |
114 |
115 |
7
116 |
Dirk
117 |
Anderson
118 |
119 |
120 |
8
121 |
Chris
122 |
Stevenson
123 |
124 |
125 |
9
126 |
Bernard
127 |
Sutherland
128 |
129 |
130 |
10
131 |
Kate
132 |
Pinkerton
133 |
134 |
135 |
136 |
137 |
138 | Back...
139 |
140 |
--------------------------------------------------------------------------------
/Website/ReadMe.txt:
--------------------------------------------------------------------------------
1 | //-----------------------------------------------------------------------
2 | // Part of the LINQ to JavaScript (JSLINQ) v2.x Project - https://github.com/crpietschmann/jslinq
3 | // Copyright (C) 2012-2023 Chris Pietschmann (http://pietschsoft.com)
4 | // This license can be found here: https://github.com/crpietschmann/jslinq/blob/master/LICENSE
5 | //-----------------------------------------------------------------------
6 |
7 | LINQ To JavaScript Project - https://github.com/crpietschmann/jslinq
8 |
9 | To Run the Interactive SDK:
10 | - Open up the Default.htm file in a web browser
11 |
12 | To include JSLINQ within a website:
13 | - 1) Copy the JSLINQ.js file into your website
14 | - 2) Place the following script tag in the Head of your web page:
15 |
16 |
17 |
18 | JSLINQ Change Log
19 | -----------------
20 | Version 2.3 (11/17/2023)
21 | -------------
22 | - Cleaned up Javascript code to be a little more clean as per modern javascript standards
23 | - Updated License and other links to point to Github project
24 | - Add `forEach(callback)` function to JSLINQ object
25 |
26 | Version 2.2
27 | -------------
28 | - Added lower case "jslinq" option that can be used interchangably with "JSLINQ"
29 |
30 | - Added lower case options for the operator methods (ex: .where = .Where, .select = .Select, .orderBy = .OrderBy) that can be used interchangably with the upper case options.
31 |
32 | - added a couple more fixes recommended by jslint, plus made TestSamples.htm run test automatically on page load
33 |
34 | - Fixed js code, ala http://www.jslint.com
35 |
36 | - Add ".Random(count)" method to return a random set of elements
37 |
38 | - modified "new Array()" calls to "[]", and "new Object()" to "{}" to make the code cleaner
39 |
40 | - Added ".Each" method
41 |
42 | - Modified ".Select" to accept multiple fields to select by passing them in as a delimited string.
43 |
44 | - Added "Skip" method to Bypasses a specified number of elements in a sequence and then returns the remaining elements.
45 |
46 | - Added "Take" method to return the first 'n' number of elements in the array.
47 |
48 | - Modify "OrderBy" and "OrderByDescending" to access "C#-like Lambda" expressions also.
49 | var sample = JSLINQ(Samples.People)
50 | .OrderBy("item => item.FirstName");
51 |
52 | - Modify "Select" to accept fields/properties to select by passing in a string.
53 | var sample = JSLINQ(Samples.People)
54 | .Select("FirstName");
55 | OR
56 | var sample = JSLINQ(Samples.People)
57 | .Select("ID,FirstName,LastName");
58 |
59 | - Modify "OrderByDescending" to accept the field/property to order by as a string in addition to accepting a "clause function"/lambda expression.
60 | var sample = JSLINQ(Samples.People)
61 | .OrderByDescending("FirstName");
62 |
63 | - Modify "OrderBy" to accept the field/property to order by as a string in addition to accepting a "clause function"/lambda expression.
64 | var sample = JSLINQ(Samples.People)
65 | .OrderBy("FirstName");
66 |
67 | - Select method fix: Stop calling "clause" twice for each iteration of an element. This improves performance of calling "Select".
68 | - Modify all "clauses" / lambda expressions to get called having "this" equal to the Array Item where appropriate.
69 | var exampleArray = JSLINQ(myList)
70 | .Where(function(){ return this.FirstName == "Chris"; })
71 | .OrderBy(function() { return this.FirstName; })
72 | .Select(function(){ return this.FirstName; });
73 |
74 | - Replace all "new JSLINQ()" usage with "JSLINQ()" in JSLINQ.js file. Helps make file smaller and utilizes the new method of calling JSLINQ.
75 | - Replaced "index" variable name with "i" for iterator loops in JSLINQ.js. Just to make the file a little bit smaller.
76 |
77 |
78 | Version 2.10 (4/20/2015)
79 | -------------
80 | - Modified the JSLINQ object to allow you to create an instance of JSLINQ containing an Array of elements
81 | using either of the following methods:
82 | var option1 = JSLINQ(myArray);
83 | var option2 = new JSLINQ(myArray);
84 |
85 | - Added an extensibility example; located at "/Examples/Extensions/get.htm"
86 | - Added Improved Intellisense Support and moved it to the "JSLINQ-vsdoc.js" file.
87 |
88 |
89 | Version 2.00
90 | -------------
91 | - Removed use of "eval" method
92 | - Added an example of search an HTML DOM Table using JSLINQ
93 | - Placed all functionality within the global JSLINQ object. This is to improve possible compatibility with other
94 | javascript frameworks (like jQuery and ASP.NET AJAX).
95 |
96 |
97 | Version 1.03
98 | ------------
99 | - Added Intersect Operator
100 | - Added DefaultIfEmpty Operator
101 | - Added ElementAtOrDefault Operator
102 | - Added FirstOrDefault Operator
103 | - Added LastOrDefault Operator
104 | - Started adding Usage Examples
105 | -- Count Word Occurrences
106 | -- Count Set of Words
107 |
108 | Version 1.02
109 | ------------
110 | - A few Bug fixes that were revealed with Unit Tests
111 | - Interactive SDK Created
112 | - Unit Test Created
113 | --- Intial testing of the Samples Unit Tests yielded the following speed results for all tests:
114 | ------ IE7: ~10 milliseconds
115 | ------ FireFox 2: ~10 milliseconds
116 | ------ Safari 3 for Windows: ~4 milliseconds
117 |
118 | Version 1.01
119 | ------------
120 | - Added the OrderByDescending Operator
121 | - Added the SelectMany Operator
122 | - Added the Count Operator
123 | - Added the Distinct Operator
124 | - Added the Any Operator
125 | - Added the All Operator
126 | - Made it so you can access the elements "index" within the clause/predicate of each of the following Operators: Where, Count, Any, All
127 | - Added the Reverse Operator, this also allows access to the elements "index" within the clause/predicate
128 | - Added First Operator, this also allows access to the elements "index" within the clause/predicate
129 | - Added Last Operator, this also allows access to the elements "index" within the clause/predicate
130 | - Added ElementAt Operator
131 | - Added Concat Operator - this is identical to JavaScripts Array.concat method
132 |
133 | Version 1.00
134 | ------------
135 | Operators
136 | - From
137 | - Where
138 | - OrderBy
139 | - Select
--------------------------------------------------------------------------------
/Website/Examples/Extensions/get.htm:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | JSLINQ Extensibility Example: "get" method
6 |
7 |
21 |
22 |
23 |
24 |
42 |
57 |
58 |
59 |
JSLINQ Extensibility Example: "get" method
60 |
This is an example of adding a "get" method to the JSLINQ object that works similarly to the "ElementAtOrDefault" method.
61 |
To use this sample "get" plugin, just pass in the "index" and "defaultValue" parameters the same as you would with the "ElementAtOrDefault" method. You can get the First element by omitting the "index" parameter.
62 |
63 |
Plugin Source Code:
64 |
65 |
68 |
69 |
70 |
Example Usage:
71 |
72 |
73 |
74 |
75 |
The full list of data that is being selected by the below example usages are located to the right.
168 |
169 |
170 |
171 | Back...
172 |
173 |
174 |
--------------------------------------------------------------------------------
/Website/scripts/JSLINQ-vsdoc.js:
--------------------------------------------------------------------------------
1 | //-----------------------------------------------------------------------
2 | // Visual Studio JavaScript Intellisense Helper for LINQ to JavaScript
3 | // LINQ to JavaScript (JSLINQ) Project - https://github.com/crpietschmann/jslinq
4 | // Copyright (c) 2012-2023 Chris Pietschmann (http://pietschsoft.com)
5 | // This license can be found here: https://github.com/crpietschmann/jslinq/blob/master/LICENSE
6 | //-----------------------------------------------------------------------
7 | JSLINQ = function(dataItems) {
8 | /// The JSLINQ Object that provides LINQ query syntax to work with JavaScript Arrays.
9 | /// The Array that this JSLINQ instance will work with.
10 | /// The internal Array that contains the actual data items.
11 | ///
12 | };
13 | JSLINQ.prototype = {
14 | ToArray: function () {
15 | /// Gets the underlieing Array object that holds the data.
16 | ///
17 | },
18 | Where: function (clause) {
19 | /// Filters a sequence of values based on a clause predicate.
20 | /// The clause used to determine query matches.
21 | ///
22 | },
23 | Select: function (clause) {
24 | /// Projects each element of a sequence into a new form.
25 | /// The clause used to determine what values to select. Or a comma delimited string containing the object properties to select.
26 | ///
27 | },
28 | OrderBy: function (clause) {
29 | /// Sorts the elements of a sequence in ascending order.
30 | /// The clause used to determine how to order the data.
31 | ///
32 | },
33 | OrderByDescending: function (clause) {
34 | /// Sorts the elements of a sequence in descending order.
35 | /// The clause used to determine how to order the data.
36 | ///
37 | },
38 | SelectMany: function (clause) {
39 | /// Projects each element of a sequence to a JSLINQ and flattens the resulting sequences into one sequence.
40 | /// The clause used to determine what values to select.
41 | ///
42 | },
43 | Count: function (clause) {
44 | /// Returns the number of elements in a sequence.
45 | /// The clause used to determine what values to count.
46 | ///
47 | },
48 | Distinct: function (clause) {
49 | /// Returns distinct elements from a sequence.
50 | /// The clause used to determine what values to select.
51 | ///
52 | },
53 | Any: function (clause) {
54 | /// Determines whether any element of a sequence exists or satisfies a condition.
55 | /// The clause used to determine if a match exists.
56 | ///
57 | },
58 | All: function (clause) {
59 | /// Determines whether all elements of a sequence satisfy a condition.
60 | /// The clause used to determine if a match exists.
61 | /// true if every element of the source sequence passes the test in the specified clause predicate, or if the sequence is empty; otherwise, false.
62 | },
63 | Reverse: function () {
64 | /// Inverts the order of the elements in a sequence.
65 | ///
66 | },
67 | First: function (clause) {
68 | /// Returns the first element of a sequence.
69 | /// The clause used to determine which group of elements to return the first element from.
70 | ///
71 | },
72 | Last: function (clause) {
73 | /// Returns the last element of a sequence.
74 | /// The clause used to determine which group of elements to return the last element from.
75 | ///
76 | },
77 | ElementAt: function (index) {
78 | /// Returns the element at a specified index in a sequence.
79 | /// The zero-based index of the element to retrieve.
80 | ///
81 | },
82 | Concat: function (array) {
83 | /// Concatenates two sequences. (Is actually Idendical to the Array.concat method.)
84 | /// A JSLINQ or Array object that contains the elements to concatenate.
85 | ///
86 | },
87 | Intersect: function (secondArray, clause) {
88 | /// Produces the set intersection of two sequences.
89 | /// The second JSLINQ element sequence to perform the Intersect on.
90 | ///
91 | ///
92 | },
93 | DefaultIfEmpty: function (defaultValue) {
94 | /// Returns the JSLINQ object, or a default value if the sequence is empty.
95 | /// The default value to return if the sequence is empty.
96 | },
97 | ElementAtOrDefault: function (index, defaultValue) {
98 | /// Returns the element at a specified index in a sequence or a default value if the index is out of range.
99 | /// The zero-based index of the element to retrieve.
100 | /// The default value to return if the index is out of range.
101 | /// defaultValue if the index is outside the bounds of the source sequence; otherwise, the element at the specified position in the source sequense.
102 | },
103 | FirstOrDefault: function (defaultValue) {
104 | /// Returns the first element of a sequence, or a default value if no element is found.
105 | /// The default value to return if no element is found.
106 | },
107 | LastOrDefault: function (defaultValue) {
108 | /// Returns the last element of a sequence, or a default value if no element is found.
109 | /// The default value to return if no element is found.
110 | },
111 | Take: function (count) {
112 | /// Returns a specified number of contiguous elements from the start of a sequence.
113 | /// The number of elements to return.
114 | },
115 | Skip: function (count) {
116 | /// Bypasses a specified number of elements in a sequence and then returns the remaining elements.
117 | /// The number of elements to skip before returning the remaining elements.
118 | },
119 | Each: function (clause) {
120 | /// Executes a clause predicate on each element.
121 | /// The clause to execute on each element.
122 | },
123 | Random: function (count) {
124 | /// This method will returns the specified number of elements at random. If no number is specified, then 1 is returned.
125 | /// The number of elements to return
126 | }
127 | };
--------------------------------------------------------------------------------
/Nuget/package/Content/Scripts/JSLINQ-vsdoc.js:
--------------------------------------------------------------------------------
1 | //-----------------------------------------------------------------------
2 | // Visual Studio JavaScript Intellisense Helper for LINQ to JavaScript
3 | // LINQ to JavaScript (JSLINQ) Project - https://github.com/crpietschmann/jslinq
4 | // Copyright (c) 2012-2023 Chris Pietschmann (http://pietschsoft.com)
5 | // This license can be found here: https://github.com/crpietschmann/jslinq/blob/master/LICENSE
6 | //-----------------------------------------------------------------------
7 | JSLINQ = function(dataItems) {
8 | /// The JSLINQ Object that provides LINQ query syntax to work with JavaScript Arrays.
9 | /// The Array that this JSLINQ instance will work with.
10 | /// The internal Array that contains the actual data items.
11 | ///
12 | };
13 | JSLINQ.prototype = {
14 | ToArray: function () {
15 | /// Gets the underlieing Array object that holds the data.
16 | ///
17 | },
18 | Where: function (clause) {
19 | /// Filters a sequence of values based on a clause predicate.
20 | /// The clause used to determine query matches.
21 | ///
22 | },
23 | Select: function (clause) {
24 | /// Projects each element of a sequence into a new form.
25 | /// The clause used to determine what values to select. Or a comma delimited string containing the object properties to select.
26 | ///
27 | },
28 | OrderBy: function (clause) {
29 | /// Sorts the elements of a sequence in ascending order.
30 | /// The clause used to determine how to order the data.
31 | ///
32 | },
33 | OrderByDescending: function (clause) {
34 | /// Sorts the elements of a sequence in descending order.
35 | /// The clause used to determine how to order the data.
36 | ///
37 | },
38 | SelectMany: function (clause) {
39 | /// Projects each element of a sequence to a JSLINQ and flattens the resulting sequences into one sequence.
40 | /// The clause used to determine what values to select.
41 | ///
42 | },
43 | Count: function (clause) {
44 | /// Returns the number of elements in a sequence.
45 | /// The clause used to determine what values to count.
46 | ///
47 | },
48 | Distinct: function (clause) {
49 | /// Returns distinct elements from a sequence.
50 | /// The clause used to determine what values to select.
51 | ///
52 | },
53 | Any: function (clause) {
54 | /// Determines whether any element of a sequence exists or satisfies a condition.
55 | /// The clause used to determine if a match exists.
56 | ///
57 | },
58 | All: function (clause) {
59 | /// Determines whether all elements of a sequence satisfy a condition.
60 | /// The clause used to determine if a match exists.
61 | /// true if every element of the source sequence passes the test in the specified clause predicate, or if the sequence is empty; otherwise, false.
62 | },
63 | Reverse: function () {
64 | /// Inverts the order of the elements in a sequence.
65 | ///
66 | },
67 | First: function (clause) {
68 | /// Returns the first element of a sequence.
69 | /// The clause used to determine which group of elements to return the first element from.
70 | ///
71 | },
72 | Last: function (clause) {
73 | /// Returns the last element of a sequence.
74 | /// The clause used to determine which group of elements to return the last element from.
75 | ///
76 | },
77 | ElementAt: function (index) {
78 | /// Returns the element at a specified index in a sequence.
79 | /// The zero-based index of the element to retrieve.
80 | ///
81 | },
82 | Concat: function (array) {
83 | /// Concatenates two sequences. (Is actually Idendical to the Array.concat method.)
84 | /// A JSLINQ or Array object that contains the elements to concatenate.
85 | ///
86 | },
87 | Intersect: function (secondArray, clause) {
88 | /// Produces the set intersection of two sequences.
89 | /// The second JSLINQ element sequence to perform the Intersect on.
90 | ///
91 | ///
92 | },
93 | DefaultIfEmpty: function (defaultValue) {
94 | /// Returns the JSLINQ object, or a default value if the sequence is empty.
95 | /// The default value to return if the sequence is empty.
96 | },
97 | ElementAtOrDefault: function (index, defaultValue) {
98 | /// Returns the element at a specified index in a sequence or a default value if the index is out of range.
99 | /// The zero-based index of the element to retrieve.
100 | /// The default value to return if the index is out of range.
101 | /// defaultValue if the index is outside the bounds of the source sequence; otherwise, the element at the specified position in the source sequense.
102 | },
103 | FirstOrDefault: function (defaultValue) {
104 | /// Returns the first element of a sequence, or a default value if no element is found.
105 | /// The default value to return if no element is found.
106 | },
107 | LastOrDefault: function (defaultValue) {
108 | /// Returns the last element of a sequence, or a default value if no element is found.
109 | /// The default value to return if no element is found.
110 | },
111 | Take: function (count) {
112 | /// Returns a specified number of contiguous elements from the start of a sequence.
113 | /// The number of elements to return.
114 | },
115 | Skip: function (count) {
116 | /// Bypasses a specified number of elements in a sequence and then returns the remaining elements.
117 | /// The number of elements to skip before returning the remaining elements.
118 | },
119 | Each: function (clause) {
120 | /// Executes a clause predicate on each element.
121 | /// The clause to execute on each element.
122 | },
123 | Random: function (count) {
124 | /// This method will returns the specified number of elements at random. If no number is specified, then 1 is returned.
125 | /// The number of elements to return
126 | }
127 | };
--------------------------------------------------------------------------------
/Website/scripts/JSLINQ.js:
--------------------------------------------------------------------------------
1 | //-----------------------------------------------------------------------
2 | // LINQ to JavaScript (JSLINQ) Project - https://github.com/crpietschmann/jslinq
3 | // Copyright (c) 2012-2023 Chris Pietschmann (http://pietschsoft.com)
4 | // This license can be found here: https://github.com/crpietschmann/jslinq/blob/master/LICENSE
5 | //-----------------------------------------------------------------------
6 | (function () {
7 | var JSLINQ = window.jslinq = window.JSLINQ = function (dataItems) {
8 | return new JSLINQ.fn.init(dataItems);
9 | },
10 | utils = {
11 | processLambda: function (clause) {
12 | if (utils.isLambda(clause)) {
13 | var expr = clause.match(/^[(\s]*([^()]*?)[)\s]*=>(.*)/);
14 | return new Function(expr[1], "return (" + expr[2] + ")");
15 | }
16 | return clause;
17 | },
18 | isLambda: function (clause) {
19 | return (clause.indexOf("=>") > -1);
20 | },
21 | randomIndex: function (max, existing) {
22 | var q, r, f = function () { return this == r; };
23 | if (!existing) {
24 | return parseInt(Math.random() * max, 10);
25 | } else {
26 | q = JSLINQ(existing);
27 | r = -1;
28 | while (r < 0 || q.Where(f).Count() !== 0) {
29 | r = utils.randomIndex(max);
30 | }
31 | return r;
32 | }
33 | }
34 | };
35 | JSLINQ.fn = JSLINQ.prototype = {
36 | init: function (dataItems) {
37 | this.items = dataItems;
38 | },
39 |
40 | // The current version of JSLINQ being used
41 | jslinq: '2.30',
42 |
43 | toArray: function () { return this.items; },
44 | forEach: function (callback) {
45 | this.items.forEach(callback);
46 | return this;
47 | },
48 | where: function (clause) {
49 | var newArray = [];
50 | // The clause was passed in as a Method that return a Boolean
51 | this.forEach((item, i) => {
52 | if (clause.apply(item, [item, i])) newArray[newArray.length] = item;
53 | });
54 | return JSLINQ(newArray);
55 | },
56 | select: function (clause) {
57 | var newArray = [], field = clause;
58 | if (typeof (clause) !== "function") {
59 | if (clause.indexOf(",") === -1) {
60 | clause = function () { return this[field]; };
61 | } else {
62 | clause = function () {
63 | var obj = {};
64 | field.split(',').forEach((f) => {
65 | obj[f] = this[f];
66 | });
67 | return obj;
68 | };
69 | }
70 | }
71 |
72 | // The clause was passed in as a Method that returns a Value
73 | this.forEach((item, i) => {
74 | val = clause.apply(item, [item]);
75 | if (val) newArray[newArray.length] = val;
76 | });
77 | return JSLINQ(newArray);
78 | },
79 | orderBy: function (clause) {
80 | var tempArray = [];
81 | this.forEach((item) => {
82 | tempArray.push(item);
83 | });
84 |
85 | if (typeof (clause) !== "function") {
86 | var field = clause;
87 | if (utils.isLambda(field)) {
88 | clause = utils.processLambda(field);
89 | } else {
90 | clause = function () { return this[field]; };
91 | }
92 | }
93 |
94 | return JSLINQ(tempArray.sort(function (a, b) {
95 | var x = clause.apply(a, [a]), y = clause.apply(b, [b]);
96 | return ((x < y) ? -1 : ((x > y) ? 1 : 0));
97 | })
98 | );
99 | },
100 | orderByDescending: function (clause) {
101 | var tempArray = [], field;
102 | this.forEach((item) => {
103 | tempArray.push(item);
104 | });
105 |
106 | if (typeof (clause) !== "function") {
107 | field = clause;
108 | if (utils.isLambda(field)) {
109 | clause = utils.processLambda(field);
110 | } else {
111 | clause = function () { return this[field]; };
112 | }
113 | }
114 |
115 | return JSLINQ(tempArray.sort(function (a, b) {
116 | var x = clause.apply(b, [b]), y = clause.apply(a, [a]);
117 | return ((x < y) ? -1 : ((x > y) ? 1 : 0));
118 | }));
119 | },
120 | selectMany: function (clause) {
121 | var r = [];
122 | this.forEach((item) => {
123 | r = r.concat(clause.apply(item, [item]));
124 | });
125 | return JSLINQ(r);
126 | },
127 | count: function (clause) {
128 | if (clause === undefined) {
129 | return this.items.length;
130 | }
131 | return this.Where(clause).items.length;
132 | },
133 | distinct: function (clause) {
134 | var dict = {}, retVal = [];
135 | this.forEach((item) => {
136 | var val = clause.apply(item, [item]);
137 | // TODO - This doesn't correctly compare Objects. Need to fix this
138 | if (dict[val] === undefined) {
139 | dict[val] = true;
140 | retVal.push(val);
141 | }
142 | });
143 | dict = null;
144 | return JSLINQ(retVal);
145 | },
146 | any: function (clause) {
147 | var item;
148 | for (var i = 0; i < this.items.length; i++) {
149 | item = this.items[i];
150 | if (clause.apply(item, [item, i])) return true;
151 | }
152 | return false;
153 | },
154 | all: function (clause) {
155 | for (var i = 0; i < this.items.length; i++) {
156 | if (!clause(this.items[i], i)) return false;
157 | }
158 | return true;
159 | },
160 | reverse: function () {
161 | var retVal = [];
162 | for (var i = this.items.length - 1; i > -1; i--) {
163 | retVal[retVal.length] = this.items[i];
164 | }
165 | return JSLINQ(retVal);
166 | },
167 | first: function (clause) {
168 | if (clause !== undefined) {
169 | return this.Where(clause).First();
170 | } else if (this.items.length > 0) {
171 | // If no clause was specified, then return the First element in the Array
172 | return this.items[0];
173 | }
174 | return null;
175 | },
176 | last: function (clause) {
177 | if (clause !== undefined) {
178 | return this.Where(clause).Last();
179 | } else {
180 | // If no clause was specified, then return the First element in the Array
181 | if (this.items.length > 0) {
182 | return this.items[this.items.length - 1];
183 | }
184 | }
185 | return null;
186 | },
187 | elementAt: function (i) {
188 | return this.items[i];
189 | },
190 | concat: function (array) {
191 | var arr = array.items || array;
192 | return JSLINQ(this.items.concat(arr));
193 | },
194 | intersect: function (secondArray, clause) {
195 | var method, sa = (secondArray.items || secondArray), result = [];
196 | if (clause !== undefined) {
197 | method = clause;
198 | } else {
199 | method = (item, i1, item2, i2) => item === item2;
200 | }
201 |
202 | for (var a = 0; a < this.items.length; a++) {
203 | for (var b = 0; b < sa.length; b++) {
204 | if (method(this.items[a], a, sa[b], b)) {
205 | result[result.length] = this.items[a];
206 | }
207 | }
208 | }
209 | return JSLINQ(result);
210 | },
211 | defaultIfEmpty: function (defaultValue) {
212 | if (this.items.length === 0) {
213 | return defaultValue;
214 | }
215 | return this;
216 | },
217 | elementAtOrDefault: function (i, defaultValue) {
218 | if (i >= 0 && i < this.items.length) {
219 | return this.items[i];
220 | }
221 | return defaultValue;
222 | },
223 | firstOrDefault: function (defaultValue) {
224 | return this.First() || defaultValue;
225 | },
226 | lastOrDefault: function (defaultValue) {
227 | return this.Last() || defaultValue;
228 | },
229 | take: function (count) {
230 | return this.Where(function (item, index) { return index < count; });
231 | },
232 | skip: function (count) {
233 | return this.Where(function (item, index) { return index >= count; });
234 | },
235 | each: function (clause) {
236 | var len = this.items.length;
237 | for (var i = 0; i < len; i++) {
238 | clause.apply(this.items[i], [this.items[i], i]);
239 | }
240 | return this;
241 | },
242 | random: function (count) {
243 | var len = this.Count(), rnd = [];
244 | if (!count) { count = 1; }
245 | for (var i = 0; i < count; i++) {
246 | rnd.push(utils.randomIndex(len - 1, rnd));
247 | }
248 | rnd = JSLINQ(rnd);
249 | return this.Where(function (item, index) {
250 | return rnd.Where(function () {
251 | return this == index;
252 | }).Count() > 0;
253 | });
254 | }
255 | };
256 |
257 | (function (fn) {
258 | fn.ToArray = fn.toArray;
259 | fn.ForEach = fn.forEach;
260 | fn.Where = fn.where;
261 | fn.Select = fn.select;
262 | fn.OrderBy = fn.orderBy;
263 | fn.OrderByDescending = fn.orderByDescending;
264 | fn.SelectMany = fn.selectMany;
265 | fn.Count = fn.count;
266 | fn.Distinct = fn.distinct;
267 | fn.Any = fn.any;
268 | fn.All = fn.all;
269 | fn.Reverse = fn.reverse;
270 | fn.First = fn.first;
271 | fn.Last = fn.last;
272 | fn.ElementAt = fn.elementAt;
273 | fn.Concat = fn.concat;
274 | fn.Intersect = fn.intersect;
275 | fn.DefaultIfEmpty = fn.defaultIfEmpty;
276 | fn.ElementAtOrDefault = fn.elementAtOrDefault;
277 | fn.FirstOrDefault = fn.firstOrDefault;
278 | fn.LastOrDefault = fn.lastOrDefault;
279 | fn.Take = fn.take;
280 | fn.Skip = fn.skip;
281 | fn.Each = fn.each;
282 | fn.Random = fn.random;
283 | })(JSLINQ.fn);
284 |
285 | JSLINQ.fn.init.prototype = JSLINQ.fn;
286 | })();
--------------------------------------------------------------------------------
/Nuget/package/Content/Scripts/JSLINQ.js:
--------------------------------------------------------------------------------
1 | //-----------------------------------------------------------------------
2 | // LINQ to JavaScript (JSLINQ) Project - https://github.com/crpietschmann/jslinq
3 | // Copyright (c) 2012-2023 Chris Pietschmann (http://pietschsoft.com)
4 | // This license can be found here: https://github.com/crpietschmann/jslinq/blob/master/LICENSE
5 | //-----------------------------------------------------------------------
6 | (function () {
7 | var JSLINQ = window.jslinq = window.JSLINQ = function (dataItems) {
8 | return new JSLINQ.fn.init(dataItems);
9 | },
10 | utils = {
11 | processLambda: function (clause) {
12 | if (utils.isLambda(clause)) {
13 | var expr = clause.match(/^[(\s]*([^()]*?)[)\s]*=>(.*)/);
14 | return new Function(expr[1], "return (" + expr[2] + ")");
15 | }
16 | return clause;
17 | },
18 | isLambda: function (clause) {
19 | return (clause.indexOf("=>") > -1);
20 | },
21 | randomIndex: function (max, existing) {
22 | var q, r, f = function () { return this == r; };
23 | if (!existing) {
24 | return parseInt(Math.random() * max, 10);
25 | } else {
26 | q = JSLINQ(existing);
27 | r = -1;
28 | while (r < 0 || q.Where(f).Count() !== 0) {
29 | r = utils.randomIndex(max);
30 | }
31 | return r;
32 | }
33 | }
34 | };
35 | JSLINQ.fn = JSLINQ.prototype = {
36 | init: function (dataItems) {
37 | this.items = dataItems;
38 | },
39 |
40 | // The current version of JSLINQ being used
41 | jslinq: '2.30',
42 |
43 | toArray: function () { return this.items; },
44 | forEach: function (callback) {
45 | this.items.forEach(callback);
46 | return this;
47 | },
48 | where: function (clause) {
49 | var newArray = [];
50 | // The clause was passed in as a Method that return a Boolean
51 | this.forEach((item, i) => {
52 | if (clause.apply(item, [item, i])) newArray[newArray.length] = item;
53 | });
54 | return JSLINQ(newArray);
55 | },
56 | select: function (clause) {
57 | var newArray = [], field = clause;
58 | if (typeof (clause) !== "function") {
59 | if (clause.indexOf(",") === -1) {
60 | clause = function () { return this[field]; };
61 | } else {
62 | clause = function () {
63 | var obj = {};
64 | field.split(',').forEach((f) => {
65 | obj[f] = this[f];
66 | });
67 | return obj;
68 | };
69 | }
70 | }
71 |
72 | // The clause was passed in as a Method that returns a Value
73 | this.forEach((item, i) => {
74 | val = clause.apply(item, [item]);
75 | if (val) newArray[newArray.length] = val;
76 | });
77 | return JSLINQ(newArray);
78 | },
79 | orderBy: function (clause) {
80 | var tempArray = [];
81 | this.forEach((item) => {
82 | tempArray.push(item);
83 | });
84 |
85 | if (typeof (clause) !== "function") {
86 | var field = clause;
87 | if (utils.isLambda(field)) {
88 | clause = utils.processLambda(field);
89 | } else {
90 | clause = function () { return this[field]; };
91 | }
92 | }
93 |
94 | return JSLINQ(tempArray.sort(function (a, b) {
95 | var x = clause.apply(a, [a]), y = clause.apply(b, [b]);
96 | return ((x < y) ? -1 : ((x > y) ? 1 : 0));
97 | })
98 | );
99 | },
100 | orderByDescending: function (clause) {
101 | var tempArray = [], field;
102 | this.forEach((item) => {
103 | tempArray.push(item);
104 | });
105 |
106 | if (typeof (clause) !== "function") {
107 | field = clause;
108 | if (utils.isLambda(field)) {
109 | clause = utils.processLambda(field);
110 | } else {
111 | clause = function () { return this[field]; };
112 | }
113 | }
114 |
115 | return JSLINQ(tempArray.sort(function (a, b) {
116 | var x = clause.apply(b, [b]), y = clause.apply(a, [a]);
117 | return ((x < y) ? -1 : ((x > y) ? 1 : 0));
118 | }));
119 | },
120 | selectMany: function (clause) {
121 | var r = [];
122 | this.forEach((item) => {
123 | r = r.concat(clause.apply(item, [item]));
124 | });
125 | return JSLINQ(r);
126 | },
127 | count: function (clause) {
128 | if (clause === undefined) {
129 | return this.items.length;
130 | }
131 | return this.Where(clause).items.length;
132 | },
133 | distinct: function (clause) {
134 | var dict = {}, retVal = [];
135 | this.forEach((item) => {
136 | var val = clause.apply(item, [item]);
137 | // TODO - This doesn't correctly compare Objects. Need to fix this
138 | if (dict[val] === undefined) {
139 | dict[val] = true;
140 | retVal.push(val);
141 | }
142 | });
143 | dict = null;
144 | return JSLINQ(retVal);
145 | },
146 | any: function (clause) {
147 | var item;
148 | for (var i = 0; i < this.items.length; i++) {
149 | item = this.items[i];
150 | if (clause.apply(item, [item, i])) return true;
151 | }
152 | return false;
153 | },
154 | all: function (clause) {
155 | for (var i = 0; i < this.items.length; i++) {
156 | if (!clause(this.items[i], i)) return false;
157 | }
158 | return true;
159 | },
160 | reverse: function () {
161 | var retVal = [];
162 | for (var i = this.items.length - 1; i > -1; i--) {
163 | retVal[retVal.length] = this.items[i];
164 | }
165 | return JSLINQ(retVal);
166 | },
167 | first: function (clause) {
168 | if (clause !== undefined) {
169 | return this.Where(clause).First();
170 | } else if (this.items.length > 0) {
171 | // If no clause was specified, then return the First element in the Array
172 | return this.items[0];
173 | }
174 | return null;
175 | },
176 | last: function (clause) {
177 | if (clause !== undefined) {
178 | return this.Where(clause).Last();
179 | } else {
180 | // If no clause was specified, then return the First element in the Array
181 | if (this.items.length > 0) {
182 | return this.items[this.items.length - 1];
183 | }
184 | }
185 | return null;
186 | },
187 | elementAt: function (i) {
188 | return this.items[i];
189 | },
190 | concat: function (array) {
191 | var arr = array.items || array;
192 | return JSLINQ(this.items.concat(arr));
193 | },
194 | intersect: function (secondArray, clause) {
195 | var method, sa = (secondArray.items || secondArray), result = [];
196 | if (clause !== undefined) {
197 | method = clause;
198 | } else {
199 | method = (item, i1, item2, i2) => item === item2;
200 | }
201 |
202 | for (var a = 0; a < this.items.length; a++) {
203 | for (var b = 0; b < sa.length; b++) {
204 | if (method(this.items[a], a, sa[b], b)) {
205 | result[result.length] = this.items[a];
206 | }
207 | }
208 | }
209 | return JSLINQ(result);
210 | },
211 | defaultIfEmpty: function (defaultValue) {
212 | if (this.items.length === 0) {
213 | return defaultValue;
214 | }
215 | return this;
216 | },
217 | elementAtOrDefault: function (i, defaultValue) {
218 | if (i >= 0 && i < this.items.length) {
219 | return this.items[i];
220 | }
221 | return defaultValue;
222 | },
223 | firstOrDefault: function (defaultValue) {
224 | return this.First() || defaultValue;
225 | },
226 | lastOrDefault: function (defaultValue) {
227 | return this.Last() || defaultValue;
228 | },
229 | take: function (count) {
230 | return this.Where(function (item, index) { return index < count; });
231 | },
232 | skip: function (count) {
233 | return this.Where(function (item, index) { return index >= count; });
234 | },
235 | each: function (clause) {
236 | var len = this.items.length;
237 | for (var i = 0; i < len; i++) {
238 | clause.apply(this.items[i], [this.items[i], i]);
239 | }
240 | return this;
241 | },
242 | random: function (count) {
243 | var len = this.Count(), rnd = [];
244 | if (!count) { count = 1; }
245 | for (var i = 0; i < count; i++) {
246 | rnd.push(utils.randomIndex(len - 1, rnd));
247 | }
248 | rnd = JSLINQ(rnd);
249 | return this.Where(function (item, index) {
250 | return rnd.Where(function () {
251 | return this == index;
252 | }).Count() > 0;
253 | });
254 | }
255 | };
256 |
257 | (function (fn) {
258 | fn.ToArray = fn.toArray;
259 | fn.ForEach = fn.forEach;
260 | fn.Where = fn.where;
261 | fn.Select = fn.select;
262 | fn.OrderBy = fn.orderBy;
263 | fn.OrderByDescending = fn.orderByDescending;
264 | fn.SelectMany = fn.selectMany;
265 | fn.Count = fn.count;
266 | fn.Distinct = fn.distinct;
267 | fn.Any = fn.any;
268 | fn.All = fn.all;
269 | fn.Reverse = fn.reverse;
270 | fn.First = fn.first;
271 | fn.Last = fn.last;
272 | fn.ElementAt = fn.elementAt;
273 | fn.Concat = fn.concat;
274 | fn.Intersect = fn.intersect;
275 | fn.DefaultIfEmpty = fn.defaultIfEmpty;
276 | fn.ElementAtOrDefault = fn.elementAtOrDefault;
277 | fn.FirstOrDefault = fn.firstOrDefault;
278 | fn.LastOrDefault = fn.lastOrDefault;
279 | fn.Take = fn.take;
280 | fn.Skip = fn.skip;
281 | fn.Each = fn.each;
282 | fn.Random = fn.random;
283 | })(JSLINQ.fn);
284 |
285 | JSLINQ.fn.init.prototype = JSLINQ.fn;
286 | })();
--------------------------------------------------------------------------------
/Website/scripts/Samples.js:
--------------------------------------------------------------------------------
1 | ///
2 | //-----------------------------------------------------------------------
3 | // Part of the LINQ to JavaScript (JSLINQ) v2.x Project - https://github.com/crpietschmann/jslinq
4 | // Copyright (C) 2012-2023 Chris Pietschmann (http://pietschsoft.com)
5 | // This license can be found here: https://github.com/crpietschmann/jslinq/blob/master/LICENSE
6 | //-----------------------------------------------------------------------
7 | var Samples = {};
8 |
9 | /* *** Arrays that Sample Code Uses *** */
10 | Samples.People = [
11 | { ID: 1, FirstName: "Chris", LastName: "Pearson", BookIDs: [1001, 1002, 1003] },
12 | { ID: 2, FirstName: "Kate", LastName: "Johnson", BookIDs: [2001, 2002, 2003] },
13 | { ID: 3, FirstName: "Josh", LastName: "Sutherland", BookIDs: [3001, 3002, 3003] },
14 | { ID: 4, FirstName: "John", LastName: "Ronald", BookIDs: [4001, 4002, 4003] },
15 | { ID: 5, FirstName: "Steve", LastName: "Pinkerton", BookIDs: [1001, 1002, 1003] },
16 | { ID: 6, FirstName: "Katie", LastName: "Zimmerman", BookIDs: [2001, 2002, 2003] },
17 | { ID: 7, FirstName: "Dirk", LastName: "Anderson", BookIDs: [3001, 3002, 3003] },
18 | { ID: 8, FirstName: "Chris", LastName: "Stevenson", BookIDs: [4001, 4002, 4003] },
19 | { ID: 9, FirstName: "Bernard", LastName: "Sutherland", BookIDs: [1001, 2002, 3003] },
20 | { ID: 10, FirstName: "Kate", LastName: "Pinkerton", BookIDs: [4001, 3002, 2003] }
21 | ];
22 |
23 | /* *** Array of Samples Contained in this page *** */
24 | Samples.SampleList = [
25 | { Group: "Where Operator", Samples: ["Samples.Where01", "Samples.Where02", "Samples.Where03"] },
26 | { Group: "Select Operator", Samples: ["Samples.Select01", "Samples.Select02", "Samples.Select03"] },
27 | { Group: "SelectMany Operator", Samples: ["Samples.SelectMany01"] },
28 | { Group: "OrderBy Operator", Samples: ["Samples.OrderBy01", "Samples.OrderBy02", "Samples.OrderBy03"] },
29 | { Group: "OrderByDescending Operator", Samples: ["Samples.OrderByDescending01", "Samples.OrderByDescending02", "Samples.OrderByDescending03"] },
30 | { Group: "All Operator", Samples: ["Samples.All01", "Samples.All02"] },
31 | { Group: "Any Operator", Samples: ["Samples.Any01", "Samples.Any02"] },
32 | { Group: "Count Operator", Samples: ["Samples.Count01", "Samples.Count02", "Samples.Count03"] },
33 | { Group: "DefaultIfEmpty Operator", Samples: ["Samples.DefaultIfEmpty01", "Samples.DefaultIfEmpty02"] },
34 | { Group: "Distinct Operator", Samples: ["Samples.Distinct01"] },
35 | { Group: "ElementAt Operator", Samples: ["Samples.ElementAt01"] },
36 | { Group: "ElementAtOrDefault Operator", Samples: ["Samples.ElementAtOrDefault01"] },
37 | { Group: "First Operator", Samples: ["Samples.First01", "Samples.First02"] },
38 | { Group: "FirstOrDefault Operator", Samples: ["Samples.FirstOrDefault01"] },
39 | { Group: "Intersect Operator", Samples: ["Samples.Intersect01", "Samples.Intersect02", "Samples.Intersect03"] },
40 | { Group: "Last Operator", Samples: ["Samples.Last01", "Samples.Last02"] },
41 | { Group: "LastOrDefault Operator", Samples: ["Samples.LastOrDefault01"] },
42 | { Group: "Reverse Operator", Samples: ["Samples.Reverse01"] },
43 | { Group: "Take", Samples: ["Samples.Take01"] },
44 | { Group: "Skip", Samples: ["Samples.Skip01"] },
45 | { Group: "Each", Samples: ["Samples.Each01"] },
46 | { Group: "Random", Samples: ["Samples.Random01", "Samples.Random02"] },
47 | { Group: "Other Unit Tests", Samples: ["Samples.OtherUnitTests01","Samples.OtherUnitTests02","Samples.OtherUnitTests03"] }
48 | ];
49 |
50 |
51 | /* *** Code used for executing and showing the samples in the page *** */
52 | Samples.ShowSampleList = function() {
53 | var sampleList = document.getElementById("SampleList");
54 | for (var g = 0; g < Samples.SampleList.length; g++) {
55 | var group = document.createElement("li");
56 | group.innerHTML = Samples.SampleList[g].Group;
57 | sampleList.appendChild(group);
58 | group = document.createElement("ul");
59 |
60 | for (var s = 0; s < Samples.SampleList[g].Samples.length; s++) {
61 | var sample = eval("new " + Samples.SampleList[g].Samples[s] + "()");
62 |
63 | var sampleElement = document.createElement("li");
64 | sampleElement.innerHTML = "" + sample.Name + "";
65 | group.appendChild(sampleElement);
66 | }
67 |
68 | sampleList.appendChild(group);
69 | }
70 | };
71 | Samples.ShowSourceData = function(){
72 | document.getElementById("SourceData").innerHTML = Samples.Views.People(Samples.People);
73 | };
74 | Samples.Show = function(sample) {
75 | if (typeof sample === "string") { sample = eval(sample); }
76 | var s = new sample();
77 | // Display Sample Name, Description and Code on the page
78 | document.getElementById("lblSampleTitle").innerHTML = s.Title;
79 | document.getElementById("lblSampleDescription").innerHTML = s.Description;
80 | document.getElementById("txtSampleCode").value = s.Code;
81 | // Execute the Sample to prove it works
82 | var results = s.Code();
83 | document.getElementById("ResultData").innerHTML = s.View(results.items || results);
84 | };
85 | Samples.RunTests = function(){
86 | var failureCount = 0;
87 | var successCount = 0;
88 | var strFailedTest = "";
89 |
90 | var start = (new Date()).getTime();
91 |
92 | Samples.SampleList.forEach((sampleList) => {
93 | sampleList.Samples.forEach((sample) => {
94 | var s = eval("new " + sample + "()");
95 | try {
96 | var result = s.Test();
97 | if (result) {
98 | successCount++;
99 | } else {
100 | failureCount++;
101 | strFailedTest += sample + " ";
102 | }
103 | } catch (error) {
104 | console.error(`Unit Test: ${sample} - ${error}`);
105 | failureCount++;
106 | strFailedTest += sample + " ";
107 | }
108 | });
109 | });
110 |
111 | var end = (new Date()).getTime();
112 |
113 | var elem = document.getElementById("TestResults");
114 | elem.innerHTML = "Successes: " + successCount + " - Failures: " + failureCount + " - Timing: " + (end - start);
115 | if (failureCount > 0) {
116 | elem.innerHTML += " Failed Tests: " + strFailedTest;
117 | }
118 | };
119 |
120 | Samples.Views = {};
121 | Samples.Views.People = function(people) {
122 | var str = "
ID
First Name
Last Name
Books
";
123 | if (people.length == undefined)
124 | {
125 | /// If the length of the people array is undefined, then it's not an array but a Person object instead.
126 | str += "