mirror of
https://github.com/enso-org/enso.git
synced 2024-11-22 22:10:15 +03:00
Tidy up the public module level statics (#6032)
Tidies up a lot of PUBLIC module statics - marked some as PRIVATE, made some methods of types.
This commit is contained in:
parent
1b30a5275f
commit
dd009fd1af
1
.github/CODEOWNERS
vendored
1
.github/CODEOWNERS
vendored
@ -23,6 +23,7 @@ Cargo.toml
|
||||
# GUI
|
||||
/app/gui/ @MichaelMauderer @wdanilo @farmaazon @mwu-tow @kazcw
|
||||
/app/gui/view/ @MichaelMauderer @wdanilo @farmaazon @kazcw
|
||||
/app/gui/view/graph-editor/src/builtin/visualization/java_script/ @MichaelMauderer @wdanilo @farmaazon @kazcw @jdunkerley
|
||||
/app/ide-desktop/ @MichaelMauderer @wdanilo @kazcw
|
||||
|
||||
# Engine (old)
|
||||
|
@ -160,7 +160,7 @@ class TableVisualization extends Visualization {
|
||||
rowData = parsedData.json
|
||||
dataTruncated = parsedData.all_rows_count !== parsedData.json.length
|
||||
} else if (parsedData.json != null && isObjectMatrix(parsedData.json)) {
|
||||
let firstKeys = Object.keys(data[0])
|
||||
let firstKeys = Object.keys(parsedData.json[0])
|
||||
columnDefs = firstKeys.map(field => ({ field }))
|
||||
rowData = parsedData.json.map(obj =>
|
||||
firstKeys.reduce((acc, key) => ({ ...acc, [key]: toRender(obj[key]) }), {})
|
||||
|
@ -268,23 +268,37 @@ make_field_name_selector : JS_Object -> Display -> Single_Choice
|
||||
make_field_name_selector js_object display=Display.Always =
|
||||
Single_Choice display=display values=(js_object.field_names.map n->(Option n n.pretty))
|
||||
|
||||
## PRIVATE
|
||||
Make a new JavaScript object.
|
||||
foreign js new_object = """
|
||||
return {}
|
||||
|
||||
## PRIVATE
|
||||
Parse a text value into JavaScript object.
|
||||
foreign js json_parse text = """
|
||||
return JSON.parse(text)
|
||||
|
||||
## PRIVATE
|
||||
Convert a JavaScript object to a text value.
|
||||
foreign js json_stringify js_object = """
|
||||
return JSON.stringify(js_object)
|
||||
|
||||
## PRIVATE
|
||||
Check a JavaScript object has a given property.
|
||||
foreign js has_property js_object key = """
|
||||
return js_object.hasOwnProperty(key)
|
||||
|
||||
## PRIVATE
|
||||
Get a value from a JavaScript object.
|
||||
foreign js get_value object key = """
|
||||
return object[key]
|
||||
|
||||
## PRIVATE
|
||||
Set a value on a JavaScript object and return the new object.
|
||||
foreign js set_value object key value = """
|
||||
return {...object, [key]: value}
|
||||
|
||||
## PRIVATE
|
||||
Gets all the property names of a JavaScript object.
|
||||
foreign js get_property_names object = """
|
||||
return Object.getOwnPropertyNames(object)
|
||||
|
@ -10,7 +10,7 @@ from project.Data.Boolean import True, False
|
||||
|
||||
polyglot java import org.enso.base.ObjectComparator
|
||||
|
||||
## ADVANCED
|
||||
## PRIVATE
|
||||
Creates a Java Comparator object which can call back to Enso for comparison
|
||||
of non-primitive types.
|
||||
|
||||
@ -26,7 +26,7 @@ new custom_comparator=Nothing =
|
||||
Nothing -> ObjectComparator.getInstance (comparator_to_java Ordering.compare)
|
||||
_ -> ObjectComparator.new (comparator_to_java custom_comparator)
|
||||
|
||||
## ADVANCED
|
||||
## PRIVATE
|
||||
Create a Java Comparator with the specified Text_Ordering
|
||||
|
||||
Arguments:
|
||||
|
@ -13,7 +13,7 @@ import project.Error.Error
|
||||
import project.Meta
|
||||
import project.Nothing.Nothing
|
||||
import project.Panic.Panic
|
||||
import project.Polyglot
|
||||
import project.Polyglot.Polyglot
|
||||
|
||||
from project.Data.Boolean import Boolean, True, False
|
||||
|
||||
|
@ -22,7 +22,6 @@ import project.Math
|
||||
import project.Meta
|
||||
import project.Nothing.Nothing
|
||||
import project.Panic.Panic
|
||||
import project.Polyglot
|
||||
|
||||
from project.Data.Boolean import Boolean, True, False
|
||||
from project.Data.Time.Date_Time import ensure_in_epoch
|
||||
|
@ -14,8 +14,8 @@ import project.Math
|
||||
import project.Meta
|
||||
import project.Nothing.Nothing
|
||||
import project.Panic.Panic
|
||||
import project.Polyglot
|
||||
import project.Polyglot.Java
|
||||
import project.Polyglot.Polyglot
|
||||
import project.Runtime
|
||||
import project.System
|
||||
import project.System.Environment
|
||||
@ -44,8 +44,8 @@ export project.Math
|
||||
export project.Meta
|
||||
export project.Nothing.Nothing
|
||||
export project.Panic.Panic
|
||||
export project.Polyglot
|
||||
export project.Polyglot.Java
|
||||
export project.Polyglot.Polyglot
|
||||
export project.Runtime
|
||||
export project.System
|
||||
export project.System.Environment
|
||||
|
@ -14,7 +14,6 @@ import project.Nothing.Nothing
|
||||
import project.Polyglot.Java
|
||||
|
||||
import project.Error.Error as Base_Error
|
||||
import project.Polyglot as Base_Polyglot
|
||||
|
||||
from project.Data.Boolean import Boolean, True, False
|
||||
|
||||
|
@ -1,117 +1,160 @@
|
||||
## A module representing interactions with polyglot languages.
|
||||
Polyglot is a term that refers to other languages (such as Java) that are
|
||||
running on the same JVM.
|
||||
|
||||
import project.Any.Any
|
||||
import project.Data.Array.Array
|
||||
import project.Data.Boolean.Boolean
|
||||
import project.Data.Numbers.Integer
|
||||
import project.Data.Text.Text
|
||||
import project.Data.Vector.Vector
|
||||
import project.Nothing.Nothing
|
||||
import project.Runtime.Source_Location.Source_Location
|
||||
|
||||
@Builtin_Type
|
||||
type Polyglot
|
||||
## Reads the number of elements in a given polyglot array object.
|
||||
|
||||
## Reads the number of elements in a given polyglot array object.
|
||||
Arguments:
|
||||
- array: a polyglot array object, originating in any supported language.
|
||||
get_array_size : Any -> Integer
|
||||
get_array_size array = @Builtin_Method "Polyglot.get_array_size"
|
||||
|
||||
Arguments:
|
||||
- array: a polyglot array object, originating in any supported language.
|
||||
get_array_size : Any -> Integer
|
||||
get_array_size array = @Builtin_Method "Polyglot.get_array_size"
|
||||
## Reads the element in a given polyglot array object.
|
||||
|
||||
## Reads the element in a given polyglot array object.
|
||||
Arguments:
|
||||
- index: The index to get the element from.
|
||||
read_array_element : Any -> Integer -> Any
|
||||
read_array_element array index = @Builtin_Method "Polyglot.read_array_element"
|
||||
|
||||
Arguments:
|
||||
- index: The index to get the element from.
|
||||
read_array_element : Any -> Integer -> Any
|
||||
read_array_element array index = @Builtin_Method "Polyglot.read_array_element"
|
||||
## Executes a polyglot function object (e.g. a lambda).
|
||||
|
||||
## Executes a polyglot function object (e.g. a lambda).
|
||||
Arguments:
|
||||
- callable: The polyglot function object to execute.
|
||||
- arguments: A vector of arguments to callable.
|
||||
execute : Any -> Vector -> Any
|
||||
execute callable arguments = @Builtin_Method "Polyglot.execute"
|
||||
|
||||
Arguments:
|
||||
- callable: The polyglot function object to execute.
|
||||
- arguments: A vector of arguments to callable.
|
||||
execute : Any -> Vector -> Any
|
||||
execute callable arguments = @Builtin_Method "Polyglot.execute"
|
||||
## Performs a by-name lookup for a member in a polyglot object.
|
||||
|
||||
## Performs a by-name lookup for a member in a polyglot object.
|
||||
Arguments:
|
||||
- object: The polyglot object on which to perform the member lookup.
|
||||
- member_name: The textual name of the member to lookup.
|
||||
|
||||
Arguments:
|
||||
- object: The polyglot object on which to perform the member lookup.
|
||||
- member_name: The textual name of the member to lookup.
|
||||
> Example
|
||||
Look up the field a on an object o.
|
||||
Polyglot.get_member o "a"
|
||||
get_member : Any -> Text -> Any
|
||||
get_member object member_name = @Builtin_Method "Polyglot.get_member"
|
||||
|
||||
> Example
|
||||
Look up the field a on an object o.
|
||||
Polyglot.get_member o "a"
|
||||
get_member : Any -> Text -> Any
|
||||
get_member object member_name = @Builtin_Method "Polyglot.get_member"
|
||||
## Returns a polyglot array of all of the members of the provided object.
|
||||
|
||||
## Returns a polyglot array of all of the members of the provided object.
|
||||
Arguments:
|
||||
- object: The object from which to get a list of member names.
|
||||
|
||||
Arguments:
|
||||
- object: The object from which to get a list of member names.
|
||||
> Example
|
||||
Get a list of the fields for an object o.
|
||||
Polyglot.get_members o
|
||||
get_members : Any -> Array
|
||||
get_members object = @Builtin_Method "Polyglot.get_members"
|
||||
|
||||
> Example
|
||||
Get a list of the fields for an object o.
|
||||
Polyglot.get_members o
|
||||
get_members : Any -> Array
|
||||
get_members object = @Builtin_Method "Polyglot.get_members"
|
||||
## Instantiates a polyglot object using the provided constructor.
|
||||
|
||||
## Instantiates a polyglot object using the provided constructor.
|
||||
Arguments:
|
||||
- constructor: The constructor with which to instantiate the object.
|
||||
- arguments: A vector of the arguments to pass to the polyglot
|
||||
constructor.
|
||||
|
||||
Arguments:
|
||||
- constructor: The constructor with which to instantiate the object.
|
||||
- arguments: A vector of the arguments to pass to the polyglot
|
||||
constructor.
|
||||
> Example
|
||||
Instantiate a new Java Integer with the value 1.
|
||||
Polyglot.new Integer [1]
|
||||
new : Any -> Vector -> Any
|
||||
new constructor arguments = @Builtin_Method "Polyglot.new"
|
||||
|
||||
> Example
|
||||
Instantiate a new Java Integer with the value 1.
|
||||
Polyglot.new Integer [1]
|
||||
new : Any -> Vector -> Any
|
||||
new constructor arguments = @Builtin_Method "Polyglot.new"
|
||||
## Invokes a method on a polyglot object by name.
|
||||
|
||||
## Invokes a method on a polyglot object by name.
|
||||
Arguments:
|
||||
- target: The polyglot object on which to call the method.
|
||||
- name: The name of the method.
|
||||
- arguments: The arguments to pass to the method given by name.
|
||||
invoke : Any -> Text -> Vector -> Any
|
||||
invoke target name arguments = @Builtin_Method "Polyglot.invoke"
|
||||
|
||||
Arguments:
|
||||
- target: The polyglot object on which to call the method.
|
||||
- name: The name of the method.
|
||||
- arguments: The arguments to pass to the method given by name.
|
||||
invoke : Any -> Text -> Vector -> Any
|
||||
invoke target name arguments = @Builtin_Method "Polyglot.invoke"
|
||||
## ADVANCED
|
||||
UNSTABLE
|
||||
|
||||
## ADVANCED
|
||||
UNSTABLE
|
||||
Checks if `value` defines a source location.
|
||||
|
||||
Checks if `value` defines a source location.
|
||||
Source locations are typically exposed by functions, classes, sometimes
|
||||
also other objects to specify their allocation sites.
|
||||
has_source_location : Any -> Boolean
|
||||
has_source_location value = @Builtin_Method "Polyglot.has_source_location"
|
||||
|
||||
Source locations are typically exposed by functions, classes, sometimes
|
||||
also other objects to specify their allocation sites.
|
||||
has_source_location : Any -> Boolean
|
||||
has_source_location value = @Builtin_Method "Polyglot.has_source_location"
|
||||
## ADVANCED
|
||||
UNSTABLE
|
||||
|
||||
## ADVANCED
|
||||
UNSTABLE
|
||||
Gets the source location of `value`.
|
||||
|
||||
Gets the source location of `value`.
|
||||
Source locations are typically exposed by functions, classes, sometimes
|
||||
also other objects to specify their allocation sites.
|
||||
This method will throw a polyglot exception if
|
||||
`Polyglot.has_source_location value` returns `False`.
|
||||
get_source_location : Any -> Source_Location
|
||||
get_source_location value = @Builtin_Method "Polyglot.get_source_location"
|
||||
|
||||
Source locations are typically exposed by functions, classes, sometimes
|
||||
also other objects to specify their allocation sites.
|
||||
This method will throw a polyglot exception if
|
||||
`Polyglot.has_source_location value` returns `False`.
|
||||
get_source_location : Any -> Source_Location
|
||||
get_source_location value = @Builtin_Method "Polyglot.get_source_location"
|
||||
## Checks if a polyglot language is installed in the runtime environment.
|
||||
|
||||
## Checks if a polyglot language is installed in the runtime environment.
|
||||
Arguments:
|
||||
- langauge_name: The name of the language to test
|
||||
is_language_installed : Text -> Boolean
|
||||
is_language_installed language_name = @Builtin_Method "Polyglot.is_language_installed"
|
||||
|
||||
Arguments:
|
||||
- langauge_name: The name of the language to test
|
||||
is_language_installed : Text -> Boolean
|
||||
is_language_installed language_name = @Builtin_Method "Polyglot.is_language_installed"
|
||||
## ADVANCED
|
||||
UNSTABLE
|
||||
|
||||
## ADVANCED
|
||||
UNSTABLE
|
||||
Returns the executable name of a polyglot object.
|
||||
get_executable_name : Any -> Text
|
||||
get_executable_name value = @Builtin_Method "Polyglot.get_executable_name"
|
||||
|
||||
Returns the executable name of a polyglot object.
|
||||
get_executable_name : Any -> Text
|
||||
get_executable_name value = @Builtin_Method "Polyglot.get_executable_name"
|
||||
## Utilities for working with Java polyglot objects.
|
||||
type Java
|
||||
## Adds the provided entry to the host class path.
|
||||
|
||||
Arguments:
|
||||
- path: The java classpath entry to add.
|
||||
|
||||
Use of the actual polyglot imports system should be preferred to use of
|
||||
this method.
|
||||
|
||||
> Example
|
||||
Adding Random to the classpath.
|
||||
|
||||
Java.add_to_class_path "java.util.Random"
|
||||
add_to_class_path : Text -> Nothing
|
||||
add_to_class_path path = @Builtin_Method "Java.add_to_class_path"
|
||||
|
||||
## Looks up a java symbol on the classpath by name.
|
||||
|
||||
Arguments:
|
||||
- name: The name of the java symbol to look up.
|
||||
|
||||
Use of the actual polyglot imports system should be preferred to use of
|
||||
this method.
|
||||
|
||||
> Example
|
||||
Look up java's Random class.
|
||||
|
||||
Java.lookup_class "java.util.Random"
|
||||
lookup_class : Text -> Any
|
||||
lookup_class name = @Builtin_Method "Java.lookup_class"
|
||||
|
||||
## PRIVATE
|
||||
|
||||
Checks whether an object is an instance of a given class.
|
||||
|
||||
Arguments:
|
||||
- object: The object to check for class membership.
|
||||
- class: The java class to check for membership in.
|
||||
is_instance : Any -> Any -> Boolean
|
||||
is_instance object class =
|
||||
class_object = class.class
|
||||
class_object.isInstance object
|
||||
|
@ -1,48 +0,0 @@
|
||||
## Utilities for working with Java polyglot objects.
|
||||
|
||||
import project.Any.Any
|
||||
import project.Data.Boolean.Boolean
|
||||
import project.Data.Text.Text
|
||||
import project.Nothing.Nothing
|
||||
|
||||
## Adds the provided entry to the host class path.
|
||||
|
||||
Arguments:
|
||||
- path: The java classpath entry to add.
|
||||
|
||||
Use of the actual polyglot imports system should be preferred to use of
|
||||
this method.
|
||||
|
||||
> Example
|
||||
Adding Random to the classpath.
|
||||
|
||||
Java.add_to_class_path "java.util.Random"
|
||||
add_to_class_path : Text -> Nothing
|
||||
add_to_class_path path = @Builtin_Method "Java.add_to_class_path"
|
||||
|
||||
## Looks up a java symbol on the classpath by name.
|
||||
|
||||
Arguments:
|
||||
- name: The name of the java symbol to look up.
|
||||
|
||||
Use of the actual polyglot imports system should be preferred to use of
|
||||
this method.
|
||||
|
||||
> Example
|
||||
Look up java's Random class.
|
||||
|
||||
Java.lookup_class "java.util.Random"
|
||||
lookup_class : Text -> Any
|
||||
lookup_class name = @Builtin_Method "Java.lookup_class"
|
||||
|
||||
## PRIVATE
|
||||
|
||||
Checks whether an object is an instance of a given class.
|
||||
|
||||
Arguments:
|
||||
- object: The object to check for class membership.
|
||||
- class: The java class to check for membership in.
|
||||
is_instance : Any -> Any -> Boolean
|
||||
is_instance object class =
|
||||
class_object = class.class
|
||||
class_object.isInstance object
|
@ -3,7 +3,7 @@ import project.Data.Array.Array
|
||||
import project.Data.Text.Text
|
||||
import project.Data.Vector.Vector
|
||||
import project.Nothing.Nothing
|
||||
import project.Polyglot
|
||||
import project.Polyglot.Polyglot
|
||||
import project.Runtime.Source_Location.Source_Location
|
||||
|
||||
from project.Data.Index_Sub_Range.Index_Sub_Range import First, Last
|
||||
|
@ -7,7 +7,7 @@ import project.Data.Pair.Pair
|
||||
import project.Data.Vector.Vector
|
||||
import project.Error.Error
|
||||
import project.Nothing.Nothing
|
||||
import project.Polyglot
|
||||
import project.Polyglot.Polyglot
|
||||
import project.Runtime
|
||||
import project.Runtime.Source_Location.Source_Location
|
||||
import project.Runtime.Stack_Trace_Element
|
||||
|
@ -6,51 +6,6 @@ import Standard.Table.Internal.Vector_Builder.Vector_Builder
|
||||
import project.Data.SQL_Type.SQL_Type
|
||||
import project.Data.SQL_Statement.SQL_Statement
|
||||
|
||||
## UNSTABLE
|
||||
|
||||
Creates a Builder representing and empty code fragment.
|
||||
empty : Builder
|
||||
empty = Builder.Value (Vector_Builder.empty)
|
||||
|
||||
## UNSTABLE
|
||||
|
||||
Creates a Builder representing a code fragment containing the specified raw
|
||||
code.
|
||||
|
||||
Arguments:
|
||||
- text: The raw SQL code.
|
||||
code : Text -> Builder
|
||||
code text =
|
||||
vec = if text.is_empty then [] else [SQL_Fragment.Code_Part text]
|
||||
Builder.Value (Vector_Builder.from_vector vec)
|
||||
|
||||
## UNSTABLE
|
||||
|
||||
Creates a Builder representing an interpolation of the given object.
|
||||
|
||||
Arguments:
|
||||
- sql_type: The expected SQL type of `object`.
|
||||
- object: The object to be interpolated into the query as if it has the type
|
||||
given by `sql_type`.
|
||||
interpolation : SQL_Type -> Any -> Builder
|
||||
interpolation sql_type object = Builder.Value (Vector_Builder.from_vector [SQL_Fragment.Interpolation sql_type object])
|
||||
|
||||
## UNSTABLE
|
||||
|
||||
Joins a vector of code fragments with the provided separator.
|
||||
|
||||
Arguments:
|
||||
- separator: The separator to use when joining the code fragments.
|
||||
- statements: The SQL statements to join using `separator`.
|
||||
join : Builder | Text -> Vector Builder -> Builder
|
||||
join separator statements =
|
||||
sep = case separator of
|
||||
Builder.Value _ -> separator
|
||||
_ -> code separator
|
||||
|
||||
if statements.length == 0 then empty else
|
||||
(1.up_to statements.length . fold (statements.at 0) acc-> i-> acc ++ sep ++ statements.at i)
|
||||
|
||||
## UNSTABLE
|
||||
|
||||
A fragment of a SQL query.
|
||||
@ -59,7 +14,6 @@ join separator statements =
|
||||
SQL_Fragment.Interpolation which represents an object that will be
|
||||
interpolated into the query.
|
||||
type SQL_Fragment
|
||||
|
||||
## UNSTABLE
|
||||
|
||||
A SQL fragment that represents raw SQL code.
|
||||
@ -80,6 +34,42 @@ type SQL_Fragment
|
||||
Interpolation sql_type:SQL_Type object:Any
|
||||
|
||||
type Builder
|
||||
## Creates a Builder representing and empty code fragment.
|
||||
empty : Builder
|
||||
empty = Builder.Value (Vector_Builder.empty)
|
||||
|
||||
## Creates a Builder representing a code fragment containing the specified raw
|
||||
code.
|
||||
|
||||
Arguments:
|
||||
- text: The raw SQL code.
|
||||
code : Text -> Builder
|
||||
code text =
|
||||
vec = if text.is_empty then [] else [SQL_Fragment.Code_Part text]
|
||||
Builder.Value (Vector_Builder.from_vector vec)
|
||||
|
||||
## Creates a Builder representing an interpolation of the given object.
|
||||
|
||||
Arguments:
|
||||
- sql_type: The expected SQL type of `object`.
|
||||
- object: The object to be interpolated into the query as if it has the type
|
||||
given by `sql_type`.
|
||||
interpolation : SQL_Type -> Any -> Builder
|
||||
interpolation sql_type object = Builder.Value (Vector_Builder.from_vector [SQL_Fragment.Interpolation sql_type object])
|
||||
|
||||
## Joins a vector of code fragments with the provided separator.
|
||||
|
||||
Arguments:
|
||||
- separator: The separator to use when joining the code fragments.
|
||||
- statements: The SQL statements to join using `separator`.
|
||||
join : Builder | Text -> Vector Builder -> Builder
|
||||
join separator statements =
|
||||
sep = case separator of
|
||||
Builder.Value _ -> separator
|
||||
_ -> Builder.code separator
|
||||
|
||||
if statements.length == 0 then Builder.empty else
|
||||
(1.up_to statements.length . fold (statements.at 0) acc-> i-> acc ++ sep ++ statements.at i)
|
||||
|
||||
## PRIVATE
|
||||
|
||||
@ -100,7 +90,7 @@ type Builder
|
||||
- other: The code fragment to append to `self`.
|
||||
++ : Builder -> Builder
|
||||
++ self other = case other of
|
||||
text : Text -> if text == "" then self else Builder.Value (self.fragments ++ (code text).fragments)
|
||||
text : Text -> if text == "" then self else Builder.Value (self.fragments ++ (Builder.code text).fragments)
|
||||
_ -> Builder.Value (self.fragments ++ other.fragments)
|
||||
|
||||
## UNSTABLE
|
||||
@ -121,7 +111,7 @@ type Builder
|
||||
|
||||
Wraps the code fragment in parentheses.
|
||||
paren : Builder
|
||||
paren self = code "(" ++ self ++ ")"
|
||||
paren self = Builder.code "(" ++ self ++ ")"
|
||||
|
||||
## UNSTABLE
|
||||
|
||||
@ -135,7 +125,7 @@ type Builder
|
||||
prefix_if_present self prefix =
|
||||
pref = case prefix of
|
||||
_ : Builder -> prefix
|
||||
_ -> code prefix
|
||||
_ -> Builder.code prefix
|
||||
if self.is_empty then self else pref++self
|
||||
|
||||
## PRIVATE
|
||||
|
@ -1548,9 +1548,8 @@ type Table
|
||||
Arguments:
|
||||
- connection: The connection to a database.
|
||||
- table_name: The name of the table to get.
|
||||
- columns: The names of the columns to get.
|
||||
- columns: List of columns to fetch. Each column is represented by a pair of column name and its expected SQL Type.
|
||||
- ctx: The context to use for the table.
|
||||
# make_table : Connection -> Text -> Vector [Text, SQL_Type] -> Context -> Table
|
||||
make_table : Connection -> Text -> Vector -> Context -> Table
|
||||
make_table connection table_name columns ctx =
|
||||
if columns.is_empty then Error.throw (Illegal_State.Error "Unexpectedly attempting to create a Database Table with no columns. This is a bug in the Database library.") else
|
||||
|
@ -1,7 +1,6 @@
|
||||
from Standard.Base import all
|
||||
import Standard.Base.Errors.Illegal_State.Illegal_State
|
||||
|
||||
import project.Data.SQL
|
||||
import project.Data.SQL.Builder
|
||||
import project.Internal.IR.Context.Context
|
||||
import project.Internal.IR.SQL_Expression.SQL_Expression
|
||||
@ -10,7 +9,6 @@ import project.Internal.IR.SQL_Join_Kind.SQL_Join_Kind
|
||||
import project.Internal.IR.Order_Descriptor.Order_Descriptor
|
||||
import project.Internal.IR.Nulls_Order.Nulls_Order
|
||||
import project.Internal.IR.Query.Query
|
||||
from project.Data.SQL import code
|
||||
|
||||
from project.Errors import Unsupported_Database_Operation
|
||||
|
||||
@ -69,7 +67,7 @@ make_unary_op name =
|
||||
arguments ->
|
||||
case arguments.length == 1 of
|
||||
True ->
|
||||
(code name+" ")++(arguments.at 0) . paren
|
||||
(Builder.code name+" ")++(arguments.at 0) . paren
|
||||
False ->
|
||||
Error.throw <| Illegal_State.Error ("Invalid amount of arguments for operation " + name)
|
||||
|
||||
@ -130,7 +128,7 @@ make_right_unary_op name =
|
||||
make_function : Text -> (Vector Builder -> Builder)
|
||||
make_function name =
|
||||
arguments ->
|
||||
(code name) ++ (SQL.join ", " arguments . paren)
|
||||
(Builder.code name) ++ (Builder.join ", " arguments . paren)
|
||||
|
||||
## PRIVATE
|
||||
|
||||
@ -142,7 +140,7 @@ make_constant : Text -> (Vector Builder -> Builder)
|
||||
make_constant sql_code =
|
||||
arguments ->
|
||||
if arguments.not_empty then Error.throw <| Illegal_State.Error "No arguments were expected" else
|
||||
code sql_code
|
||||
Builder.code sql_code
|
||||
|
||||
## PRIVATE
|
||||
|
||||
@ -157,7 +155,7 @@ make_constant sql_code =
|
||||
wrap_in_quotes : Text -> Builder
|
||||
wrap_in_quotes identifier =
|
||||
escaped = identifier.replace '"' '""'
|
||||
code '"'+escaped+'"'
|
||||
Builder.code '"'+escaped+'"'
|
||||
|
||||
## PRIVATE
|
||||
|
||||
@ -197,7 +195,7 @@ make_iif arguments = case arguments.length of
|
||||
expr = arguments.at 0
|
||||
when_true = arguments.at 1
|
||||
when_false = arguments.at 2
|
||||
(code "CASE WHEN" ++ expr ++ " THEN " ++ when_true ++ " WHEN " ++ expr ++ " IS NULL THEN NULL ELSE " ++ when_false ++ " END").paren
|
||||
(Builder.code "CASE WHEN" ++ expr ++ " THEN " ++ when_true ++ " WHEN " ++ expr ++ " IS NULL THEN NULL ELSE " ++ when_false ++ " END").paren
|
||||
_ ->
|
||||
Error.throw <| Illegal_State.Error ("Invalid amount of arguments for operation IIF")
|
||||
|
||||
@ -218,14 +216,14 @@ make_is_in arguments = case arguments.length of
|
||||
0 -> Error.throw <| Illegal_State.Error ("The operation IS_IN requires at least one argument.")
|
||||
## If only the self argument is provided, no value will ever be in the empty list, so we just short circuit to false.
|
||||
`IN ()` would be more meaningful, but it is a syntax error.
|
||||
1 -> code 'FALSE' . paren
|
||||
1 -> Builder.code 'FALSE' . paren
|
||||
_ ->
|
||||
expr = arguments.first
|
||||
list = arguments.drop 1
|
||||
is_in = expr ++ " IN (" ++ (SQL.join ", " list) ++ ")"
|
||||
is_in = expr ++ " IN (" ++ (Builder.join ", " list) ++ ")"
|
||||
## We ensure that even `NULL IN (...)` is coalesced to False, so that
|
||||
negation will work as expected.
|
||||
code "COALESCE(" ++ is_in ++ ", FALSE)"
|
||||
Builder.code "COALESCE(" ++ is_in ++ ", FALSE)"
|
||||
|
||||
## PRIVATE
|
||||
make_is_in_column : Vector Builder -> Builder
|
||||
@ -234,9 +232,9 @@ make_is_in_column arguments = case arguments.length of
|
||||
expr = arguments.at 0
|
||||
in_query = arguments.at 1
|
||||
has_nulls_query = arguments.at 2
|
||||
is_in = code "COALESCE(" ++ expr ++ " IN (" ++ in_query ++ "), FALSE)"
|
||||
is_in = Builder.code "COALESCE(" ++ expr ++ " IN (" ++ in_query ++ "), FALSE)"
|
||||
has_nulls = has_nulls_query.paren ++ " = TRUE"
|
||||
code "CASE WHEN " ++ expr ++ " IS NULL THEN " ++ has_nulls ++ " ELSE " ++ is_in ++ " END"
|
||||
Builder.code "CASE WHEN " ++ expr ++ " IS NULL THEN " ++ has_nulls ++ " ELSE " ++ is_in ++ " END"
|
||||
_ -> Error.throw <| Illegal_State.Error ("The operation IS_IN_COLUMN requires at exactly 3 arguments: the expression, the IN subquery, the subquery checking for nulls.")
|
||||
|
||||
## PRIVATE
|
||||
@ -250,7 +248,7 @@ generate_expression : Internal_Dialect -> SQL_Expression | Order_Descriptor | Qu
|
||||
generate_expression dialect expr = case expr of
|
||||
SQL_Expression.Column origin name ->
|
||||
dialect.wrap_identifier origin ++ '.' ++ dialect.wrap_identifier name
|
||||
SQL_Expression.Constant sql_type value -> SQL.interpolation sql_type value
|
||||
SQL_Expression.Constant sql_type value -> Builder.interpolation sql_type value
|
||||
SQL_Expression.Operation kind arguments ->
|
||||
op = dialect.operation_map.get kind (Error.throw <| Unsupported_Database_Operation.Error kind)
|
||||
parsed_args = arguments.map (generate_expression dialect)
|
||||
@ -269,7 +267,7 @@ generate_expression dialect expr = case expr of
|
||||
alias : Internal_Dialect -> Text -> Builder
|
||||
alias dialect name =
|
||||
wrapped = dialect.wrap_identifier name
|
||||
code " AS " ++ wrapped
|
||||
Builder.code " AS " ++ wrapped
|
||||
|
||||
## PRIVATE
|
||||
|
||||
@ -283,11 +281,11 @@ generate_from_part dialect from_spec = case from_spec of
|
||||
From_Spec.Table name as_name ->
|
||||
dialect.wrap_identifier name ++ alias dialect as_name
|
||||
From_Spec.Query raw_sql as_name ->
|
||||
code raw_sql . paren ++ alias dialect as_name
|
||||
Builder.code raw_sql . paren ++ alias dialect as_name
|
||||
From_Spec.Join kind left_spec right_spec on ->
|
||||
left = generate_from_part dialect left_spec
|
||||
right = generate_from_part dialect right_spec
|
||||
ons = SQL.join " AND " (on.map (generate_expression dialect)) . prefix_if_present " ON "
|
||||
ons = Builder.join " AND " (on.map (generate_expression dialect)) . prefix_if_present " ON "
|
||||
left ++ (" " + kind.to_sql + " ") ++ right ++ ons
|
||||
From_Spec.Sub_Query columns context as_name ->
|
||||
sub = generate_query dialect (Query.Select columns context)
|
||||
@ -295,7 +293,7 @@ generate_from_part dialect from_spec = case from_spec of
|
||||
|
||||
## PRIVATE
|
||||
fold_case = lift_unary_op "FOLD_CASE" arg->
|
||||
code "LOWER(UPPER(" ++ arg ++ "))"
|
||||
Builder.code "LOWER(UPPER(" ++ arg ++ "))"
|
||||
|
||||
## PRIVATE
|
||||
make_case_sensitive = lift_unary_op "MAKE_CASE_SENSITIVE" _->
|
||||
@ -303,7 +301,7 @@ make_case_sensitive = lift_unary_op "MAKE_CASE_SENSITIVE" _->
|
||||
|
||||
## PRIVATE
|
||||
simple_equals_ignore_case = Base_Generator.lift_binary_op "equals_ignore_case" a-> b->
|
||||
code "LOWER(UPPER(" ++ a ++ ")) = LOWER(UPPER(" ++ b ++ "))"
|
||||
Builder.code "LOWER(UPPER(" ++ a ++ ")) = LOWER(UPPER(" ++ b ++ "))"
|
||||
|
||||
## PRIVATE
|
||||
make_equals a b =
|
||||
@ -347,15 +345,15 @@ generate_select_context : Internal_Dialect -> Context -> Builder
|
||||
generate_select_context dialect ctx =
|
||||
gen_exprs exprs = exprs.map (generate_expression dialect)
|
||||
from_part = generate_from_part dialect ctx.from_spec
|
||||
where_part = (SQL.join " AND " (gen_exprs ctx.where_filters)) . prefix_if_present " WHERE "
|
||||
group_part = (SQL.join ", " (gen_exprs ctx.groups)) . prefix_if_present " GROUP BY "
|
||||
where_part = (Builder.join " AND " (gen_exprs ctx.where_filters)) . prefix_if_present " WHERE "
|
||||
group_part = (Builder.join ", " (gen_exprs ctx.groups)) . prefix_if_present " GROUP BY "
|
||||
limit_part = case ctx.limit of
|
||||
Nothing -> ""
|
||||
_ : Integer -> " LIMIT " + ctx.limit.to_text
|
||||
|
||||
orders = ctx.orders.map (generate_order dialect)
|
||||
order_part = (SQL.join ", " orders) . prefix_if_present " ORDER BY "
|
||||
(code " FROM ") ++ from_part ++ where_part ++ group_part ++ order_part ++ limit_part
|
||||
order_part = (Builder.join ", " orders) . prefix_if_present " ORDER BY "
|
||||
(Builder.code " FROM ") ++ from_part ++ where_part ++ group_part ++ order_part ++ limit_part
|
||||
|
||||
## PRIVATE
|
||||
|
||||
@ -368,11 +366,11 @@ generate_select_context dialect ctx =
|
||||
expression returning a value.
|
||||
generate_insert_query : Internal_Dialect -> Text -> Vector Any -> Builder
|
||||
generate_insert_query dialect table_name pairs =
|
||||
names = SQL.join ", " <| pairs.map (.first >> dialect.wrap_identifier)
|
||||
values = SQL.join ", " <| pairs.map (.second >> generate_expression dialect)
|
||||
names = Builder.join ", " <| pairs.map (.first >> dialect.wrap_identifier)
|
||||
values = Builder.join ", " <| pairs.map (.second >> generate_expression dialect)
|
||||
into = dialect.wrap_identifier table_name
|
||||
|
||||
code "INSERT INTO " ++ into ++ " (" ++ names ++ ") VALUES (" ++ values ++ ")"
|
||||
Builder.code "INSERT INTO " ++ into ++ " (" ++ names ++ ") VALUES (" ++ values ++ ")"
|
||||
|
||||
## PRIVATE
|
||||
|
||||
@ -386,15 +384,15 @@ generate_query dialect query = case query of
|
||||
Query.Select columns ctx ->
|
||||
gen_column pair = (generate_expression dialect pair.second) ++ alias dialect pair.first
|
||||
cols = case columns of
|
||||
Nothing -> code "*"
|
||||
_ -> SQL.join ", " (columns.map gen_column)
|
||||
Nothing -> Builder.code "*"
|
||||
_ -> Builder.join ", " (columns.map gen_column)
|
||||
prefix = case ctx.distinct_on of
|
||||
Nothing -> code ""
|
||||
Nothing -> Builder.code ""
|
||||
expressions : Vector ->
|
||||
# TODO I just realised this does not make sense in other backends than Postgres, so we should probably fail in such cases; probably rewrite into a generic modifier? or a transform?
|
||||
generated = SQL.join ", " (expressions.map (generate_expression dialect))
|
||||
code "DISTINCT ON (" ++ generated ++ ") "
|
||||
code "SELECT " ++ prefix ++ cols ++ generate_select_context dialect ctx
|
||||
generated = Builder.join ", " (expressions.map (generate_expression dialect))
|
||||
Builder.code "DISTINCT ON (" ++ generated ++ ") "
|
||||
Builder.code "SELECT " ++ prefix ++ cols ++ generate_select_context dialect ctx
|
||||
Query.Insert table_name pairs ->
|
||||
generate_insert_query dialect table_name pairs
|
||||
_ -> Error.throw <| Unsupported_Database_Operation.Error "Unsupported query type."
|
||||
@ -437,10 +435,10 @@ make_concat make_raw_concat_expr make_contains_expr has_quote args =
|
||||
includes_quote = make_contains_expr expr quote
|
||||
is_empty = expr ++ " = ''"
|
||||
needs_quoting = includes_separator.paren ++ " OR " ++ includes_quote.paren ++ " OR " ++ is_empty.paren
|
||||
escaped = code "replace(" ++ expr ++ ", " ++ quote ++ ", " ++ quote ++ append ++ quote ++ ")"
|
||||
escaped = Builder.code "replace(" ++ expr ++ ", " ++ quote ++ ", " ++ quote ++ append ++ quote ++ ")"
|
||||
quoted = quote ++ append ++ escaped ++ append ++ quote
|
||||
code "CASE WHEN " ++ needs_quoting ++ " THEN " ++ quoted ++ " ELSE " ++ expr ++ " END"
|
||||
Builder.code "CASE WHEN " ++ needs_quoting ++ " THEN " ++ quoted ++ " ELSE " ++ expr ++ " END"
|
||||
False -> expr
|
||||
transformed_expr = code "CASE WHEN " ++ expr ++ " IS NULL THEN '' ELSE " ++ possibly_quoted.paren ++ " END"
|
||||
transformed_expr = Builder.code "CASE WHEN " ++ expr ++ " IS NULL THEN '' ELSE " ++ possibly_quoted.paren ++ " END"
|
||||
concatenated = make_raw_concat_expr transformed_expr separator
|
||||
prefix.paren ++ append ++ concatenated ++ append ++ suffix.paren
|
||||
|
@ -78,6 +78,7 @@ type Join_Subquery_Setup
|
||||
self.old_columns.zip self.new_columns old-> new->
|
||||
[old.name, new]
|
||||
|
||||
## PRIVATE
|
||||
prepare_subqueries : Table -> Table -> Boolean -> Boolean -> Pair Join_Subquery_Setup
|
||||
prepare_subqueries left right needs_left_indicator needs_right_indicator =
|
||||
## If a self-join, make sure we are able to distinguish the left and
|
||||
|
@ -5,7 +5,7 @@ import Standard.Base.Runtime.Managed_Resource.Managed_Resource
|
||||
import Standard.Table.Data.Storage.Storage
|
||||
import Standard.Table.Data.Table.Table as Materialized_Table
|
||||
|
||||
import project.Data.SQL
|
||||
import project.Data.SQL.Builder
|
||||
import project.Data.SQL_Statement.SQL_Statement
|
||||
import project.Data.SQL_Type.SQL_Type
|
||||
import project.Internal.Base_Generator
|
||||
@ -195,8 +195,8 @@ create_table_statement name table temporary =
|
||||
column_names = table.columns.map .name
|
||||
col_makers = column_names.zip column_types name-> typ->
|
||||
Base_Generator.wrap_in_quotes name ++ " " ++ typ.name
|
||||
create_prefix = SQL.code <| if temporary then "CREATE TEMPORARY TABLE " else "CREATE TABLE "
|
||||
(create_prefix ++ Base_Generator.wrap_in_quotes name ++ " (" ++ (SQL.join ", " col_makers) ++ ")").build
|
||||
create_prefix = Builder.code <| if temporary then "CREATE TEMPORARY TABLE " else "CREATE TABLE "
|
||||
(create_prefix ++ Base_Generator.wrap_in_quotes name ++ " (" ++ (Builder.join ", " col_makers) ++ ")").build
|
||||
|
||||
## PRIVATE
|
||||
Returns the default database type corresponding to an in-memory storage type.
|
||||
|
@ -9,7 +9,7 @@ import Standard.Table.Internal.Problem_Builder.Problem_Builder
|
||||
from Standard.Table.Data.Aggregate_Column.Aggregate_Column import all
|
||||
|
||||
import project.Connection.Connection.Connection
|
||||
import project.Data.SQL
|
||||
import project.Data.SQL.Builder
|
||||
import project.Data.SQL_Statement.SQL_Statement
|
||||
import project.Data.SQL_Type.SQL_Type
|
||||
import project.Data.Table.Table
|
||||
@ -25,7 +25,6 @@ import project.Internal.IR.Nulls_Order.Nulls_Order
|
||||
import project.Internal.IR.SQL_Join_Kind.SQL_Join_Kind
|
||||
import project.Internal.IR.Query.Query
|
||||
|
||||
from project.Data.SQL import code
|
||||
from project.Errors import Unsupported_Database_Operation
|
||||
|
||||
## PRIVATE
|
||||
@ -152,42 +151,43 @@ resolve_target_sql_type aggregate = case aggregate of
|
||||
|
||||
## PRIVATE
|
||||
agg_count_is_null = Base_Generator.lift_unary_op "COUNT_IS_NULL" arg->
|
||||
code "COUNT(CASE WHEN " ++ arg.paren ++ " IS NULL THEN 1 END)"
|
||||
Builder.code "COUNT(CASE WHEN " ++ arg.paren ++ " IS NULL THEN 1 END)"
|
||||
|
||||
## PRIVATE
|
||||
agg_count_empty = Base_Generator.lift_unary_op "COUNT_EMPTY" arg->
|
||||
code "COUNT(CASE WHEN (" ++ arg.paren ++ " IS NULL) OR (" ++ arg.paren ++ " = '') THEN 1 END)"
|
||||
Builder.code "COUNT(CASE WHEN (" ++ arg.paren ++ " IS NULL) OR (" ++ arg.paren ++ " = '') THEN 1 END)"
|
||||
|
||||
## PRIVATE
|
||||
agg_count_not_empty = Base_Generator.lift_unary_op "COUNT_NOT_EMPTY" arg->
|
||||
code "COUNT(CASE WHEN (" ++ arg.paren ++ " IS NOT NULL) AND (" ++ arg.paren ++ " != '') THEN 1 END)"
|
||||
Builder.code "COUNT(CASE WHEN (" ++ arg.paren ++ " IS NOT NULL) AND (" ++ arg.paren ++ " != '') THEN 1 END)"
|
||||
|
||||
## PRIVATE
|
||||
agg_median = Base_Generator.lift_unary_op "MEDIAN" arg->
|
||||
median = code "percentile_cont(0.5) WITHIN GROUP (ORDER BY " ++ arg ++ ")"
|
||||
median = Builder.code "percentile_cont(0.5) WITHIN GROUP (ORDER BY " ++ arg ++ ")"
|
||||
## TODO Technically, this check may not be necessary if the input column has
|
||||
type INTEGER, because it is impossible to represent a NaN in that type.
|
||||
However, currently the column type inference is not tested well-enough to
|
||||
rely on this, so leaving an uniform approach regardless of type. This
|
||||
could be revisited when further work on column types takes place.
|
||||
See issue: https://www.pivotaltracker.com/story/show/180854759
|
||||
has_nan = code "bool_or(" ++ arg ++ " = double precision 'NaN')"
|
||||
code "CASE WHEN " ++ has_nan ++ " THEN 'NaN' ELSE " ++ median ++ " END"
|
||||
has_nan = Builder.code "bool_or(" ++ arg ++ " = double precision 'NaN')"
|
||||
Builder.code "CASE WHEN " ++ has_nan ++ " THEN 'NaN' ELSE " ++ median ++ " END"
|
||||
|
||||
## PRIVATE
|
||||
agg_mode = Base_Generator.lift_unary_op "MODE" arg->
|
||||
code "mode() WITHIN GROUP (ORDER BY " ++ arg ++ ")"
|
||||
Builder.code "mode() WITHIN GROUP (ORDER BY " ++ arg ++ ")"
|
||||
|
||||
## PRIVATE
|
||||
agg_percentile = Base_Generator.lift_binary_op "PERCENTILE" p-> expr->
|
||||
percentile = code "percentile_cont(" ++ p ++ ") WITHIN GROUP (ORDER BY " ++ expr ++ ")"
|
||||
percentile = Builder.code "percentile_cont(" ++ p ++ ") WITHIN GROUP (ORDER BY " ++ expr ++ ")"
|
||||
## TODO Technically, this check may not be necessary if the input column has
|
||||
type INTEGER, because it is impossible to represent a NaN in that type.
|
||||
However, currently the column type inference is not tested well-enough to
|
||||
rely on this, so leaving an uniform approach regardless of type. This
|
||||
could be revisited when further work on column types takes place.
|
||||
See issue: https://www.pivotaltracker.com/story/show/180854759
|
||||
has_nan = code "bool_or(" ++ expr ++ " = double precision 'NaN')"
|
||||
code "CASE WHEN " ++ has_nan ++ " THEN 'NaN' ELSE " ++ percentile ++ " END"
|
||||
has_nan = Builder.code "bool_or(" ++ expr ++ " = double precision 'NaN')"
|
||||
Builder.code "CASE WHEN " ++ has_nan ++ " THEN 'NaN' ELSE " ++ percentile ++ " END"
|
||||
|
||||
## PRIVATE
|
||||
These are written in a not most-efficient way, but a way that makes them
|
||||
@ -200,36 +200,39 @@ first_last_aggregators =
|
||||
last_not_null = make_first_aggregator reverse=True ignore_null=True
|
||||
[["FIRST", first], ["FIRST_NOT_NULL", first_not_null], ["LAST", last], ["LAST_NOT_NULL", last_not_null]]
|
||||
|
||||
## PRIVATE
|
||||
make_first_aggregator reverse ignore_null args =
|
||||
if args.length < 2 then Error.throw (Illegal_State.Error "Insufficient number of arguments for the operation.") else
|
||||
result_expr = args.first
|
||||
order_bys = args.drop 1
|
||||
|
||||
filter_clause = if ignore_null.not then "" else
|
||||
code " FILTER (WHERE " ++ result_expr.paren ++ " IS NOT NULL)"
|
||||
Builder.code " FILTER (WHERE " ++ result_expr.paren ++ " IS NOT NULL)"
|
||||
order_clause =
|
||||
code " ORDER BY " ++ SQL.join "," order_bys
|
||||
Builder.code " ORDER BY " ++ Builder.join "," order_bys
|
||||
index_expr = case reverse of
|
||||
True -> if ignore_null.not then "COUNT(*)" else
|
||||
code "COUNT(" ++ result_expr ++ ")"
|
||||
Builder.code "COUNT(" ++ result_expr ++ ")"
|
||||
False -> "1"
|
||||
|
||||
code "(array_agg(" ++ result_expr.paren ++ order_clause ++ ")" ++ filter_clause ++ ")[" ++ index_expr ++ "]"
|
||||
Builder.code "(array_agg(" ++ result_expr.paren ++ order_clause ++ ")" ++ filter_clause ++ ")[" ++ index_expr ++ "]"
|
||||
|
||||
## PRIVATE
|
||||
agg_shortest = Base_Generator.lift_unary_op "SHORTEST" arg->
|
||||
order_clause =
|
||||
code " ORDER BY char_length(" ++ arg ++ ") ASC NULLS LAST"
|
||||
code "(array_agg(" ++ arg.paren ++ order_clause ++ "))[1]"
|
||||
Builder.code " ORDER BY char_length(" ++ arg ++ ") ASC NULLS LAST"
|
||||
Builder.code "(array_agg(" ++ arg.paren ++ order_clause ++ "))[1]"
|
||||
|
||||
## PRIVATE
|
||||
agg_longest = Base_Generator.lift_unary_op "LONGEST" arg->
|
||||
order_clause =
|
||||
code " ORDER BY char_length(" ++ arg ++ ") DESC NULLS LAST"
|
||||
code "(array_agg(" ++ arg.paren ++ order_clause ++ "))[1]"
|
||||
Builder.code " ORDER BY char_length(" ++ arg ++ ") DESC NULLS LAST"
|
||||
Builder.code "(array_agg(" ++ arg.paren ++ order_clause ++ "))[1]"
|
||||
|
||||
## PRIVATE
|
||||
concat_ops =
|
||||
make_raw_concat_expr expr separator =
|
||||
code "string_agg(" ++ expr ++ ", " ++ separator ++ ")"
|
||||
Builder.code "string_agg(" ++ expr ++ ", " ++ separator ++ ")"
|
||||
concat = Base_Generator.make_concat make_raw_concat_expr make_contains_expr
|
||||
[["CONCAT", concat (has_quote=False)], ["CONCAT_QUOTE_IF_NEEDED", concat (has_quote=True)]]
|
||||
|
||||
@ -239,24 +242,24 @@ agg_count_distinct args = if args.is_empty then (Error.throw (Illegal_Argument.E
|
||||
case args.length == 1 of
|
||||
True ->
|
||||
## A single null value will be skipped.
|
||||
code "COUNT(DISTINCT " ++ args.first ++ ")"
|
||||
Builder.code "COUNT(DISTINCT " ++ args.first ++ ")"
|
||||
False ->
|
||||
## A tuple of nulls is not a null, so it will not be skipped - but
|
||||
we want to ignore all-null columns. So we manually filter them
|
||||
out.
|
||||
count = code "COUNT(DISTINCT (" ++ SQL.join ", " args ++ "))"
|
||||
count = Builder.code "COUNT(DISTINCT (" ++ Builder.join ", " args ++ "))"
|
||||
are_nulls = args.map arg-> arg.paren ++ " IS NULL"
|
||||
all_nulls_filter = code " FILTER (WHERE NOT (" ++ SQL.join " AND " are_nulls ++ "))"
|
||||
all_nulls_filter = Builder.code " FILTER (WHERE NOT (" ++ Builder.join " AND " are_nulls ++ "))"
|
||||
(count ++ all_nulls_filter).paren
|
||||
|
||||
## PRIVATE
|
||||
agg_count_distinct_include_null args =
|
||||
## If we always count as tuples, then even null fields are counted.
|
||||
code "COUNT(DISTINCT (" ++ SQL.join ", " args ++ ", 0))"
|
||||
Builder.code "COUNT(DISTINCT (" ++ Builder.join ", " args ++ ", 0))"
|
||||
|
||||
## PRIVATE
|
||||
starts_with = Base_Generator.lift_binary_op "starts_with" str-> sub->
|
||||
res = code "starts_with(" ++ str ++ "," ++ sub ++ ")"
|
||||
res = Builder.code "starts_with(" ++ str ++ "," ++ sub ++ ")"
|
||||
res.paren
|
||||
|
||||
## PRIVATE
|
||||
@ -266,11 +269,11 @@ ends_with = Base_Generator.lift_binary_op "ends_with" str-> sub->
|
||||
|
||||
## PRIVATE
|
||||
make_case_sensitive = Base_Generator.lift_unary_op "MAKE_CASE_SENSITIVE" arg->
|
||||
code "((" ++ arg ++ ') COLLATE "ucs_basic")'
|
||||
Builder.code "((" ++ arg ++ ') COLLATE "ucs_basic")'
|
||||
|
||||
## PRIVATE
|
||||
make_contains_expr expr substring =
|
||||
code "position(" ++ substring ++ " in " ++ expr ++ ") > 0"
|
||||
Builder.code "position(" ++ substring ++ " in " ++ expr ++ ") > 0"
|
||||
|
||||
## PRIVATE
|
||||
contains = Base_Generator.lift_binary_op "contains" make_contains_expr
|
||||
@ -305,11 +308,11 @@ is_nan = Base_Generator.lift_unary_op "IS_NAN" arg->
|
||||
|
||||
## PRIVATE
|
||||
bool_or = Base_Generator.lift_unary_op "BOOL_OR" arg->
|
||||
code "bool_or(" ++ arg ++ ")"
|
||||
Builder.code "bool_or(" ++ arg ++ ")"
|
||||
|
||||
## PRIVATE
|
||||
decimal_div = Base_Generator.lift_binary_op "/" x-> y->
|
||||
code "CAST(" ++ x ++ " AS double precision) / CAST(" ++ y ++ " AS double precision)"
|
||||
Builder.code "CAST(" ++ x ++ " AS double precision) / CAST(" ++ y ++ " AS double precision)"
|
||||
|
||||
## PRIVATE
|
||||
mod_op = Base_Generator.lift_binary_op "mod" x-> y->
|
||||
|
@ -8,7 +8,7 @@ import Standard.Table.Internal.Problem_Builder.Problem_Builder
|
||||
from Standard.Table.Data.Aggregate_Column.Aggregate_Column import all
|
||||
|
||||
import project.Connection.Connection.Connection
|
||||
import project.Data.SQL
|
||||
import project.Data.SQL.Builder
|
||||
import project.Data.SQL_Statement.SQL_Statement
|
||||
import project.Data.SQL_Type.SQL_Type
|
||||
import project.Data.Table.Table
|
||||
@ -22,7 +22,6 @@ import project.Internal.IR.Query.Query
|
||||
import project.Internal.Common.Database_Distinct_Helper
|
||||
import project.Internal.Common.Database_Join_Helper
|
||||
|
||||
from project.Data.SQL import code
|
||||
from project.Errors import Unsupported_Database_Operation
|
||||
|
||||
## PRIVATE
|
||||
@ -168,31 +167,31 @@ unsupported name =
|
||||
|
||||
## PRIVATE
|
||||
agg_count_is_null = Base_Generator.lift_unary_op "COUNT_IS_NULL" arg->
|
||||
code "COALESCE(SUM(" ++ arg.paren ++ " IS NULL), 0)"
|
||||
Builder.code "COALESCE(SUM(" ++ arg.paren ++ " IS NULL), 0)"
|
||||
|
||||
## PRIVATE
|
||||
agg_count_empty = Base_Generator.lift_unary_op "COUNT_EMPTY" arg->
|
||||
code "COALESCE(SUM((" ++ arg.paren ++ " IS NULL) OR (" ++ arg.paren ++ " == '')), 0)"
|
||||
Builder.code "COALESCE(SUM((" ++ arg.paren ++ " IS NULL) OR (" ++ arg.paren ++ " == '')), 0)"
|
||||
|
||||
## PRIVATE
|
||||
agg_count_not_empty = Base_Generator.lift_unary_op "COUNT_NOT_EMPTY" arg->
|
||||
code "COALESCE(SUM((" ++ arg.paren ++ " IS NOT NULL) AND (" ++ arg.paren ++ " != '')), 0)"
|
||||
Builder.code "COALESCE(SUM((" ++ arg.paren ++ " IS NOT NULL) AND (" ++ arg.paren ++ " != '')), 0)"
|
||||
|
||||
## PRIVATE
|
||||
agg_stddev_pop = Base_Generator.lift_unary_op "STDDEV_POP" arg->
|
||||
sum_of_squares = code "SUM(" ++ arg.paren ++ "*" ++ arg.paren ++ ")"
|
||||
square_of_sums = code "SUM(" ++ arg ++ ") * SUM(" ++ arg ++ ")"
|
||||
n = code "CAST(COUNT(" ++ arg ++ ") AS REAL)"
|
||||
var = code "(" ++ sum_of_squares ++ " - (" ++ square_of_sums ++ " / " ++ n ++ ")) / " ++ n
|
||||
code "SQRT(" ++ var ++ ")"
|
||||
sum_of_squares = Builder.code "SUM(" ++ arg.paren ++ "*" ++ arg.paren ++ ")"
|
||||
square_of_sums = Builder.code "SUM(" ++ arg ++ ") * SUM(" ++ arg ++ ")"
|
||||
n = Builder.code "CAST(COUNT(" ++ arg ++ ") AS REAL)"
|
||||
var = Builder.code "(" ++ sum_of_squares ++ " - (" ++ square_of_sums ++ " / " ++ n ++ ")) / " ++ n
|
||||
Builder.code "SQRT(" ++ var ++ ")"
|
||||
|
||||
## PRIVATE
|
||||
agg_stddev_samp = Base_Generator.lift_unary_op "STDDEV_SAMP" arg->
|
||||
sum_of_squares = code "SUM(" ++ arg.paren ++ "*" ++ arg.paren ++ ")"
|
||||
square_of_sums = code "SUM(" ++ arg ++ ") * SUM(" ++ arg ++ ")"
|
||||
n = code "CAST(COUNT(" ++ arg ++ ") AS REAL)"
|
||||
var = code "(" ++ sum_of_squares ++ " - (" ++ square_of_sums ++ " / " ++ n ++ ")) / (" ++ n ++ " - 1)"
|
||||
code "SQRT(" ++ var ++ ")"
|
||||
sum_of_squares = Builder.code "SUM(" ++ arg.paren ++ "*" ++ arg.paren ++ ")"
|
||||
square_of_sums = Builder.code "SUM(" ++ arg ++ ") * SUM(" ++ arg ++ ")"
|
||||
n = Builder.code "CAST(COUNT(" ++ arg ++ ") AS REAL)"
|
||||
var = Builder.code "(" ++ sum_of_squares ++ " - (" ++ square_of_sums ++ " / " ++ n ++ ")) / (" ++ n ++ " - 1)"
|
||||
Builder.code "SQRT(" ++ var ++ ")"
|
||||
|
||||
## PRIVATE
|
||||
This is a prototype that doesn't work correctly. Left for reference for
|
||||
@ -212,30 +211,30 @@ window_aggregate window_type ignore_null args =
|
||||
result_expr = args.first
|
||||
order_exprs = args.drop 1
|
||||
|
||||
filter_clause = if ignore_null.not then code "" else
|
||||
code " FILTER (WHERE " ++ result_expr.paren ++ " IS NOT NULL)"
|
||||
filter_clause = if ignore_null.not then Builder.code "" else
|
||||
Builder.code " FILTER (WHERE " ++ result_expr.paren ++ " IS NOT NULL)"
|
||||
|
||||
code window_type+"(" ++ result_expr ++ ")" ++ filter_clause ++ " OVER (ORDER BY " ++ SQL.join "," order_exprs ++ ")"
|
||||
Builder.code window_type+"(" ++ result_expr ++ ")" ++ filter_clause ++ " OVER (ORDER BY " ++ Builder.join "," order_exprs ++ ")"
|
||||
|
||||
## PRIVATE
|
||||
concat_ops =
|
||||
make_raw_concat_expr expr separator =
|
||||
code "group_concat(" ++ expr ++ ", " ++ separator ++ ")"
|
||||
Builder.code "group_concat(" ++ expr ++ ", " ++ separator ++ ")"
|
||||
concat = Base_Generator.make_concat make_raw_concat_expr make_contains_expr
|
||||
[["CONCAT", concat (has_quote=False)], ["CONCAT_QUOTE_IF_NEEDED", concat (has_quote=True)]]
|
||||
|
||||
|
||||
## PRIVATE
|
||||
agg_count_distinct args = case args.length == 1 of
|
||||
True -> code "COUNT(DISTINCT (" ++ args.first ++ "))"
|
||||
True -> Builder.code "COUNT(DISTINCT (" ++ args.first ++ "))"
|
||||
False -> Error.throw (Illegal_Argument.Error "COUNT_DISTINCT supports only single arguments in SQLite.")
|
||||
|
||||
## PRIVATE
|
||||
agg_count_distinct_include_null args = case args.length == 1 of
|
||||
True ->
|
||||
arg = args.first
|
||||
count = code "COUNT(DISTINCT " ++ arg ++ ")"
|
||||
all_nulls_case = code "CASE WHEN COUNT(CASE WHEN " ++ arg ++ "IS NULL THEN 1 END) > 0 THEN 1 ELSE 0 END"
|
||||
count = Builder.code "COUNT(DISTINCT " ++ arg ++ ")"
|
||||
all_nulls_case = Builder.code "CASE WHEN COUNT(CASE WHEN " ++ arg ++ "IS NULL THEN 1 END) > 0 THEN 1 ELSE 0 END"
|
||||
count ++ " + " ++ all_nulls_case
|
||||
False -> Error.throw (Illegal_Argument.Error "COUNT_DISTINCT supports only single arguments in SQLite.")
|
||||
|
||||
@ -251,22 +250,22 @@ ends_with = Base_Generator.lift_binary_op "ends_with" str-> sub->
|
||||
|
||||
## PRIVATE
|
||||
make_case_sensitive = Base_Generator.lift_unary_op "MAKE_CASE_SENSITIVE" arg->
|
||||
code "((" ++ arg ++ ") COLLATE BINARY)"
|
||||
Builder.code "((" ++ arg ++ ") COLLATE BINARY)"
|
||||
|
||||
## PRIVATE
|
||||
make_contains_expr expr substring =
|
||||
code "instr(" ++ expr ++ ", " ++ substring ++ ") > 0"
|
||||
Builder.code "instr(" ++ expr ++ ", " ++ substring ++ ") > 0"
|
||||
|
||||
## PRIVATE
|
||||
contains = Base_Generator.lift_binary_op "contains" make_contains_expr
|
||||
|
||||
## PRIVATE
|
||||
bool_or = Base_Generator.lift_unary_op "BOOL_OR" arg->
|
||||
code "max(" ++ arg ++ ")"
|
||||
Builder.code "max(" ++ arg ++ ")"
|
||||
|
||||
## PRIVATE
|
||||
decimal_div = Base_Generator.lift_binary_op "/" x-> y->
|
||||
code "CAST(" ++ x ++ " AS REAL) / CAST(" ++ y ++ " AS REAL)"
|
||||
Builder.code "CAST(" ++ x ++ " AS REAL) / CAST(" ++ y ++ " AS REAL)"
|
||||
|
||||
## PRIVATE
|
||||
mod_op = Base_Generator.lift_binary_op "mod" x-> y->
|
||||
|
@ -3,7 +3,8 @@ import Standard.Base.Errors.Illegal_Argument.Illegal_Argument
|
||||
|
||||
import project.Data.Image.Image
|
||||
|
||||
## List comes from org.opencv.imgcodecs.Imgcodecs#imread doc comment.
|
||||
## PRIVATE
|
||||
List comes from org.opencv.imgcodecs.Imgcodecs#imread doc comment.
|
||||
supported = [".bmp", ".dib", ".jpeg", ".jpg", ".jpe", ".jp2", ".png", ".webp", ".pbm", ".pgm", ".ppm", ".pxm", ".pnm", ".pfm", ".sr", ".ras", ".tiff", ".tif", ".exr", ".hdr", ".pic"]
|
||||
|
||||
## Read the file to a `Image` from a supported file format.
|
||||
|
@ -5,9 +5,9 @@ import Standard.Base.Errors.Unimplemented.Unimplemented
|
||||
|
||||
import project.Data.Table.Table
|
||||
import project.Delimited.Delimited_Format.Delimited_Format
|
||||
import project.Delimited.Delimited_Reader
|
||||
import project.Delimited.Delimited_Writer
|
||||
import project.Errors.Invalid_JSON_Format
|
||||
import project.Internal.Delimited_Reader
|
||||
import project.Internal.Delimited_Writer
|
||||
|
||||
Table.from (that : Text) (format:Delimited_Format = Delimited_Format.Delimited '\t') (on_problems:Problem_Behavior=Report_Warning) =
|
||||
case format of
|
||||
|
@ -4,9 +4,9 @@ import Standard.Base.Network.HTTP.Response.Response
|
||||
import project.Data.Table.Table
|
||||
import project.Data.Data_Formatter.Data_Formatter
|
||||
import project.Data.Match_Columns.Match_Columns
|
||||
import project.Delimited.Delimited_Reader
|
||||
import project.Delimited.Delimited_Writer
|
||||
import project.Delimited.Quote_Style.Quote_Style
|
||||
import project.Internal.Delimited_Reader
|
||||
import project.Internal.Delimited_Writer
|
||||
|
||||
## Read delimited files such as CSVs into a Table.
|
||||
type Delimited_Format
|
||||
|
@ -3,10 +3,10 @@ import Standard.Base.Errors.Illegal_Argument.Illegal_Argument
|
||||
|
||||
import project.Data.Table.Table
|
||||
import project.Data.Match_Columns.Match_Columns
|
||||
import project.Excel.Excel_Reader
|
||||
import project.Excel.Excel_Workbook.Excel_Workbook
|
||||
import project.Excel.Excel_Section.Excel_Section
|
||||
import project.Excel.Excel_Writer
|
||||
import project.Internal.Excel_Reader
|
||||
import project.Internal.Excel_Writer
|
||||
|
||||
## PRIVATE
|
||||
Resolve the xls_format setting to a boolean.
|
||||
|
@ -9,7 +9,7 @@ import Standard.Base.Metadata.Display
|
||||
|
||||
import project.Data.Table.Table
|
||||
import project.Excel.Excel_Range.Excel_Range
|
||||
import project.Excel.Excel_Reader
|
||||
import project.Internal.Excel_Reader
|
||||
|
||||
polyglot java import org.enso.table.read.ExcelReader
|
||||
polyglot java import org.apache.poi.ss.usermodel.Workbook
|
||||
|
@ -110,7 +110,8 @@ default_aggregate_column_name aggregate_column include_column=True =
|
||||
c = aggregate_column.column
|
||||
prefix + " " + (if include_column then c.name else "")
|
||||
|
||||
## Utility function to check if all same column
|
||||
## PRIVATE
|
||||
Utility function to check if all aggregates are operating on the same source column.
|
||||
all_same_column : Vector Aggregate_Column -> Boolean
|
||||
all_same_column aggregates =
|
||||
is_not_count c = case c of
|
||||
|
@ -24,7 +24,8 @@ polyglot java import org.enso.table.parsing.TypeInferringParser
|
||||
polyglot java import org.enso.table.read.QuoteStrippingParser
|
||||
polyglot java import org.enso.table.parsing.problems.MismatchedQuote
|
||||
|
||||
## Reads a delimited file according to the provided format.
|
||||
## PRIVATE
|
||||
Reads a delimited file according to the provided format.
|
||||
|
||||
Arguments:
|
||||
- format: The specification of the delimited file format.
|
||||
@ -45,6 +46,7 @@ read_file format file on_problems =
|
||||
result.catch Mismatched_Quote error->
|
||||
Error.throw (File_Error.Corrupted_Format file error.to_display_text error)
|
||||
|
||||
## PRIVATE
|
||||
read_text : Text -> Delimited_Format -> Problem_Behavior -> Table
|
||||
read_text text format on_problems =
|
||||
java_reader = StringReader.new text
|
||||
@ -134,6 +136,7 @@ type Detected_Headers
|
||||
## Indicates that the file exists but no headers have been found, so only positional column matching is possible.
|
||||
None (column_count : Integer)
|
||||
|
||||
## PRIVATE
|
||||
type Detected_File_Metadata
|
||||
## PRIVATE
|
||||
An internal type representing metadata describing the format of a specific
|
@ -9,8 +9,8 @@ import project.Data.Match_Columns.Match_Columns
|
||||
import project.Data.Storage.Storage
|
||||
import project.Delimited.Delimited_Format.Delimited_Format
|
||||
import project.Delimited.Quote_Style.Quote_Style
|
||||
import project.Delimited.Delimited_Reader
|
||||
import project.Delimited.Delimited_Reader.Detected_Headers
|
||||
import project.Internal.Delimited_Reader
|
||||
import project.Internal.Delimited_Reader.Detected_Headers
|
||||
import project.Internal.Java_Problems
|
||||
|
||||
from project.Errors import Column_Count_Mismatch, Column_Name_Mismatch
|
||||
@ -24,7 +24,8 @@ polyglot java import java.io.StringWriter
|
||||
polyglot java import java.io.IOException
|
||||
polyglot java import java.io.Writer
|
||||
|
||||
## Writes a delimited file according to the provided format.
|
||||
## PRIVATE
|
||||
Writes a delimited file according to the provided format.
|
||||
|
||||
Arguments:
|
||||
- table: The table to serialize.
|
@ -30,8 +30,7 @@ prepare_reader_table on_problems result_with_problems =
|
||||
|
||||
## PRIVATE
|
||||
Convert Boolean|Infer to the correct HeaderBehavior
|
||||
# TODO[DB] Fix composite types #183857386
|
||||
# make_java_headers : (Boolean | Infer) -> ExcelHeaders.HeaderBehavior
|
||||
make_java_headers : (Boolean | Infer) -> ExcelHeaders.HeaderBehavior
|
||||
make_java_headers headers = case headers of
|
||||
True -> ExcelHeaders.HeaderBehavior.USE_FIRST_ROW_AS_HEADERS
|
||||
Infer -> ExcelHeaders.HeaderBehavior.INFER
|
@ -6,7 +6,7 @@ import project.Data.Table.Table
|
||||
import project.Data.Match_Columns.Match_Columns
|
||||
import project.Excel.Excel_Range.Excel_Range
|
||||
import project.Excel.Excel_Section.Excel_Section
|
||||
import project.Excel.Excel_Reader
|
||||
import project.Internal.Excel_Reader
|
||||
from project.Errors import Invalid_Location, Range_Exceeded, Existing_Data, Column_Count_Mismatch, Column_Name_Mismatch
|
||||
|
||||
polyglot java import org.enso.table.read.ExcelReader
|
@ -1,7 +1,6 @@
|
||||
from Standard.Base import all
|
||||
|
||||
## UNSTABLE
|
||||
|
||||
## PRIVATE
|
||||
A function that throws an error to indicate that a file is being uploaded to
|
||||
`path`.
|
||||
|
||||
|
@ -143,6 +143,8 @@ Vector.default_visualization self = Id.table
|
||||
Vector.to_default_visualization_data : Text
|
||||
Vector.to_default_visualization_data self = render_vector self
|
||||
|
||||
## PRIVATE
|
||||
Internal function to convert a Vector to a JSON string.
|
||||
render_vector object depth=0 max_depth=5 max_length=100 =
|
||||
case object of
|
||||
_ : Vector -> if depth == max_depth then "[...]" else
|
||||
|
@ -36,7 +36,8 @@ type Table_Update
|
||||
Json.from_pairs [chunks, table_specification_update]
|
||||
|
||||
|
||||
## Return a sub-window of a table. The window is defined by a cell row/col and line/chunk
|
||||
## PRIVATE
|
||||
Return a sub-window of a table. The window is defined by a cell row/col and line/chunk
|
||||
coordinate as origin and the extent of the window in text chunks and lines. The size of
|
||||
a chunk (the characters in it) is defined by `chunk_width`. The output is formatted as a message
|
||||
that can be sent to the IDE's lazy text visualisation.
|
||||
@ -88,7 +89,8 @@ compute_table_update table table_cell_position text_window_position text_window_
|
||||
layout = Table_Specification_Update.Value row_heights column_widths column_names []
|
||||
Table_Update.Value chunks layout
|
||||
|
||||
## Returns a vector that contains a pairs of row index and vector of corresponding lines indices.
|
||||
## PRIVATE
|
||||
Returns a vector that contains a pairs of row index and vector of corresponding lines indices.
|
||||
compute_vertical_indices table start_row end_row start_line lines_to_get =
|
||||
## agg is a Vector of `[processed_lines, initial_offset, result_indices]`
|
||||
process_line agg row_ix =
|
||||
@ -114,7 +116,8 @@ compute_vertical_indices table start_row end_row start_line lines_to_get =
|
||||
result_agg = row_ix_iter.to_vector.fold agg process_line
|
||||
result_agg.get 2 . flatten
|
||||
|
||||
## Compute the text chunks for the row/line defined by the given indices limited to the given
|
||||
## PRIVATE
|
||||
Compute the text chunks for the row/line defined by the given indices limited to the given
|
||||
column indices. The number of chunks to get is defined by `chunks_to_get`.
|
||||
get_chunks_for_row table row_ix line_ix initial_chunk_offset column_range chunk_size chunks_to_get =
|
||||
process_cell agg column_ix =
|
||||
@ -136,27 +139,32 @@ get_chunks_for_row table row_ix line_ix initial_chunk_offset column_range chunk_
|
||||
if column_indices == [] then [] else
|
||||
(fold_map [0, initial_chunk_offset] process_cell column_indices).flatten
|
||||
|
||||
## Return the max value in the given vector.
|
||||
## PRIVATE
|
||||
Return the max value in the given vector.
|
||||
max : Vector Integer -> Integer
|
||||
max vector =
|
||||
vector.fold 0 (l -> r -> Math.max l r)
|
||||
|
||||
## Return the longest line in the given text.
|
||||
## PRIVATE
|
||||
Return the longest line in the given text.
|
||||
get_longest_line : Text -> Integer
|
||||
get_longest_line text =
|
||||
max (text.lines.map (line -> line.length))
|
||||
|
||||
## Return the length of the longest line in the given column.
|
||||
## PRIVATE
|
||||
Return the length of the longest line in the given column.
|
||||
get_column_width column =
|
||||
max (column.to_vector.map (x -> get_longest_line x.to_text))
|
||||
|
||||
## Return the height of the row defined by the given index.
|
||||
## PRIVATE
|
||||
Return the height of the row defined by the given index.
|
||||
get_row_height table row_ix =
|
||||
columns = table.columns
|
||||
row = columns.map (column -> column.at row_ix)
|
||||
max (row.map (x -> x.to_text.lines.length))
|
||||
|
||||
## Return the index of the first item in the given vector that brings the cummulative sum of items
|
||||
## PRIVATE
|
||||
Return the index of the first item in the given vector that brings the cummulative sum of items
|
||||
above the target value. If no such item exists, return `Nothing`.
|
||||
find_first_over_cum_sum : Vector Integer -> Integer -> Integer | Nothing
|
||||
find_first_over_cum_sum items target =
|
||||
@ -166,7 +174,8 @@ find_first_over_cum_sum items target =
|
||||
Not_Found -> Nothing
|
||||
value -> value.get 0
|
||||
|
||||
## Return the index of the column that is at the end of the given text width, when starting from the
|
||||
## PRIVATE
|
||||
Return the index of the column that is at the end of the given text width, when starting from the
|
||||
given start column index.
|
||||
find_end_column table start_column_ix chunks chunk_size =
|
||||
table_columns_count = table.columns.length
|
||||
@ -178,7 +187,8 @@ find_end_column table start_column_ix chunks chunk_size =
|
||||
Nothing -> table_columns_count - 1
|
||||
value -> value + start_column_ix
|
||||
|
||||
## Return the index of the row that is at the end of the given text height, when starting from the
|
||||
## PRIVATE
|
||||
Return the index of the row that is at the end of the given text height, when starting from the
|
||||
given start row index.
|
||||
find_end_row table start_row_ix max_height =
|
||||
table_row_count = (table.columns.get 0).length
|
||||
@ -189,7 +199,8 @@ find_end_row table start_row_ix max_height =
|
||||
Nothing -> table_row_count - 1
|
||||
value -> value + start_row_ix
|
||||
|
||||
## Helper for fold_map that takes a function, an accumulator value and the current item and returns
|
||||
## PRIVATE
|
||||
Helper for fold_map that takes a function, an accumulator value and the current item and returns
|
||||
a tuple of the new accumulator value and the result of the function.
|
||||
fold_map_inner f acc item =
|
||||
previous_mappings = acc.first
|
||||
@ -200,20 +211,23 @@ fold_map_inner f acc item =
|
||||
new_mappings = previous_mappings + [current_mapping]
|
||||
Pair.new new_mappings new_acc_value
|
||||
|
||||
## Map a function over a vectors, but also pass on a accumulator value from one step to the next.
|
||||
The function must return a tuple of the result of the function and the new accumulator value.
|
||||
## PRIVATE
|
||||
Map a function over a vectors, but also pass on a accumulator value from one step to the next.
|
||||
The function must return a tuple of the result of the function and the new accumulator value.
|
||||
fold_map acc f iterable =
|
||||
result = iterable.fold (Pair.new [] acc) (fold_map_inner f)
|
||||
result.first
|
||||
|
||||
## Return a vector of the cumulative sum of the given vector.
|
||||
## PRIVATE
|
||||
Return a vector of the cumulative sum of the given vector.
|
||||
map_to_cumulative_sum iterable =
|
||||
map_running_sums previous_sum current =
|
||||
running_sum = previous_sum + current
|
||||
[running_sum, running_sum]
|
||||
fold_map 0 map_running_sums iterable
|
||||
|
||||
## Return the given vector where each item is mapped to itself and its index in the vector.
|
||||
## PRIVATE
|
||||
Return the given vector where each item is mapped to itself and its index in the vector.
|
||||
enumerate : Vector Any -> Vector Any
|
||||
enumerate vector =
|
||||
(0.up_to vector.length).to_vector.zip vector
|
||||
|
@ -3,7 +3,6 @@ from Standard.Base import all
|
||||
from Standard.Base.Data.Text.Extensions import slice_text
|
||||
|
||||
## PRIVATE
|
||||
|
||||
Message to be sent to the IDE.
|
||||
type Message
|
||||
|
||||
@ -19,7 +18,8 @@ type Message
|
||||
max_line_length = ["longest_line", self.max_line_length]
|
||||
Json.from_pairs [chunks, line_count, max_line_length]
|
||||
|
||||
## Return a sub-window of a string. The window is defined by line/chunk coordinates. The size of
|
||||
## PRIVATE
|
||||
Return a sub-window of a string. The window is defined by line/chunk coordinates. The size of
|
||||
a chunk is defined by `chunk_width`. The output is formatted as a message that can be sent to
|
||||
the IDE's lazy text visualisation.
|
||||
get_lazy_visualisation_text_window text pos size chunk_width =
|
||||
|
@ -112,12 +112,13 @@ class PolyglotTest extends InterpreterTest {
|
||||
"fail to match on Polyglot symbol when imported everything from stdlib" in {
|
||||
val code =
|
||||
"""from Standard.Base import all
|
||||
|import Standard.Base.Polyglot as Polyglot_Module
|
||||
|polyglot java import java.util.Random
|
||||
|
|
||||
|main =
|
||||
| random_gen = Random.new
|
||||
| case random_gen of
|
||||
| Polyglot -> IO.println "OK"
|
||||
| Polyglot_Module -> IO.println "OK"
|
||||
| _ -> IO.println "FAIL"
|
||||
|""".stripMargin
|
||||
eval(code)
|
||||
@ -127,7 +128,7 @@ class PolyglotTest extends InterpreterTest {
|
||||
|
||||
"match on Polyglot type when explicitly importing everything from Polyglot module" in {
|
||||
val code =
|
||||
"""from Standard.Base.Polyglot import all
|
||||
"""import Standard.Base.Polyglot.Polyglot
|
||||
|import Standard.Base.IO
|
||||
|polyglot java import java.util.Random
|
||||
|
|
||||
|
@ -110,10 +110,10 @@ spec = Test.group "Pattern Matches" <|
|
||||
Test.specify "should be able to match on the Polyglot type" <|
|
||||
random_gen = Random.new
|
||||
case random_gen of
|
||||
Polyglot.Polyglot -> Nothing
|
||||
Polyglot -> Nothing
|
||||
_ -> Test.fail "Expected a polyglot object to match."
|
||||
case Polyglot.Polyglot of
|
||||
Polyglot.Polyglot -> Nothing
|
||||
case Polyglot of
|
||||
Polyglot -> Nothing
|
||||
_ -> Test.fail "Expected the Polyglot constructor to match."
|
||||
Test.specify "should be able to match on the Any type" <|
|
||||
value_1 = 1.23143
|
||||
|
@ -1,5 +1,4 @@
|
||||
polyglot java import java.time.LocalDate
|
||||
import project.Polyglot
|
||||
|
||||
new year (month = 1) (day = 1) = (LocalDate.of year month day) . internal_local_date
|
||||
|
||||
|
@ -31,12 +31,12 @@ from project.Data.Numbers export Number, Integer
|
||||
import project.Data.Vector.Vector
|
||||
export project.Data.Vector.Vector
|
||||
|
||||
import project.Polyglot
|
||||
export project.Polyglot
|
||||
|
||||
import project.Polyglot.Java
|
||||
export project.Polyglot.Java
|
||||
|
||||
import project.Polyglot.Polyglot
|
||||
export project.Polyglot.Polyglot
|
||||
|
||||
import project.Runtime
|
||||
export project.Runtime
|
||||
|
||||
|
@ -1,13 +1,15 @@
|
||||
@Builtin_Type
|
||||
type Polyglot
|
||||
get_array_size array = @Builtin_Method "Polyglot.get_array_size"
|
||||
execute callable arguments = @Builtin_Method "Polyglot.execute"
|
||||
get_member object member_name = @Builtin_Method "Polyglot.get_member"
|
||||
get_members object = @Builtin_Method "Polyglot.get_members"
|
||||
new constructor arguments = @Builtin_Method "Polyglot.new"
|
||||
invoke target name arguments = @Builtin_Method "Polyglot.invoke"
|
||||
has_source_location value = @Builtin_Method "Polyglot.has_source_location"
|
||||
get_source_location value = @Builtin_Method "Polyglot.get_source_location"
|
||||
is_language_installed language_name = @Builtin_Method "Polyglot.is_language_installed"
|
||||
get_executable_name = @Builtin_Method "Polyglot.get_executable_name"
|
||||
|
||||
get_array_size array = @Builtin_Method "Polyglot.get_array_size"
|
||||
execute callable arguments = @Builtin_Method "Polyglot.execute"
|
||||
get_member object member_name = @Builtin_Method "Polyglot.get_member"
|
||||
get_members object = @Builtin_Method "Polyglot.get_members"
|
||||
new constructor arguments = @Builtin_Method "Polyglot.new"
|
||||
invoke target name arguments = @Builtin_Method "Polyglot.invoke"
|
||||
has_source_location value = @Builtin_Method "Polyglot.has_source_location"
|
||||
get_source_location value = @Builtin_Method "Polyglot.get_source_location"
|
||||
is_language_installed language_name = @Builtin_Method "Polyglot.is_language_installed"
|
||||
get_executable_name = @Builtin_Method "Polyglot.get_executable_name"
|
||||
type Java
|
||||
lookup_class name = @Builtin_Method "Java.lookup_class"
|
||||
|
@ -1 +0,0 @@
|
||||
lookup_class name = @Builtin_Method "Java.lookup_class"
|
Loading…
Reference in New Issue
Block a user