Skip to content

Commit 00e815c

Browse files
committed
Initial commit
0 parents  commit 00e815c

File tree

12 files changed

+405
-0
lines changed

12 files changed

+405
-0
lines changed

.editorconfig

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
root = true
2+
3+
[*]
4+
charset = utf-8
5+
indent_style = tab
6+
indent_size = 4
7+
insert_final_newline = true
8+
end_of_line = lf
9+
10+
[*.{yml,yaml}]
11+
indent_style = space
12+
indent_size = 2

.github/.templateMarker

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
KOLANICH/python_project_boilerplate.py

.github/dependabot.yml

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
version: 2
2+
updates:
3+
- package-ecosystem: "pip"
4+
directory: "/"
5+
schedule:
6+
interval: "daily"
7+
allow:
8+
- dependency-type: "all"

.github/workflows/CI.yml

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
name: CI
2+
on:
3+
push:
4+
branches: [master]
5+
pull_request:
6+
branches: [master]
7+
8+
jobs:
9+
build:
10+
runs-on: ubuntu-22.04
11+
steps:
12+
- name: typical python workflow
13+
uses: KOLANICH-GHActions/typical-python-workflow@master
14+
with:
15+
github_token: ${{ secrets.GITHUB_TOKEN }}

.gitignore

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
__pycache__
2+
*.pyc
3+
*.pyo
4+
*.egg-info
5+
build
6+
dist
7+
.eggs
8+
/monkeytype.sqlite3
9+
/*.srctrldb
10+
/*.srctrlbm
11+
/*.srctrlprj

.gitlab-ci.yml

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
#image: pypy:latest
2+
image: registry.gitlab.com/kolanich-subgroups/docker-images/fixed_python:latest
3+
4+
variables:
5+
DOCKER_DRIVER: overlay2
6+
SAST_ANALYZER_IMAGE_TAG: latest
7+
SAST_DISABLE_DIND: "true"
8+
SAST_CONFIDENCE_LEVEL: 5
9+
CODECLIMATE_VERSION: latest
10+
11+
include:
12+
- template: SAST.gitlab-ci.yml
13+
- template: Code-Quality.gitlab-ci.yml
14+
- template: License-Management.gitlab-ci.yml

Code_Of_Conduct.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
No codes of conduct! Just do what you feel is right and say what you feel is right using the language you feel is right. If you feel that it is right to [make an own fork with a CoCs and SJWs](https://en.wikipedia.org/wiki/Bender_Rodriguez), just do that. We here are doing the work, not accusing each other in violating codes of conduct.

MANIFEST.in

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
include UNLICENSE
2+
include *.md
3+
include tests
4+
include .editorconfig

ReadMe.md

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
[JAbs.py] [![Unlicensed work](https://raw.githubusercontent.com/unlicense/unlicense.org/master/static/favicon.png)](https://unlicense.org/)
2+
===========
3+
![GitLab Build Status](https://gitlab.com/KOLANICH/ScalaJVMInitializer.py/badges/master/pipeline.svg)
4+
![GitLab Coverage](https://gitlab.com/KOLANICH/ScalaJVMInitializer.py/badges/master/coverage.svg)
5+
[![Coveralls Coverage](https://img.shields.io/coveralls/KOLANICH/ScalaJVMInitializer.py.svg)](https://coveralls.io/r/KOLANICH/ScalaJVMInitializer.py)
6+
[![Libraries.io Status](https://img.shields.io/librariesio/github/KOLANICH/ScalaJVMInitializer.py.svg)](https://libraries.io/github/KOLANICH/ScalaJVMInitializer.py)
7+
8+
A library complementing JAbs for doing some useful things with Scala.
9+
10+

ScalaJVMInitializer/__init__.py

Lines changed: 266 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,266 @@
1+
import typing
2+
import re
3+
from JAbs import SelectedJVMInitializer, ClassPathT, ClassesImportSpecT
4+
from collections import OrderedDict, defaultdict
5+
import warnings
6+
7+
import sys
8+
9+
decodeScalaSignature = None
10+
11+
class _ScalaMutableWrapper:
12+
__slots__ = ("_ctor", "_data")
13+
14+
def __init__(self, ji, o, template=None, ctor=None, data=None):
15+
if ctor is None:
16+
if isinstance(o, __class__):
17+
ctor = o._ctor
18+
else:
19+
ctor = o.__class__
20+
21+
self.__class__._ctor.__set__(self, ctor)
22+
23+
if data is None:
24+
if template:
25+
data = type(template)(template)
26+
else:
27+
data = ji.getSomeKindOfImmutableObjectTemplate(ctor)
28+
29+
for p in data.keys():
30+
v = getattr(o, p)()
31+
data[p] = ji.scalaWrapSomeKindOfImmutableObject(v)
32+
33+
self.__class__._data.__set__(self, data)
34+
35+
def _revertIter_(self):
36+
for v in self._revertIter():
37+
if isinstance(v, __class__):
38+
v = v._revert()
39+
yield v
40+
41+
def _revert(self):
42+
return self._ctor(list(self._revertIter()))
43+
44+
def __repr__(self):
45+
return self.__class__.__name__ + "<" + self._ctor.__name__ + ">(" + repr(self._data) + ")"
46+
47+
def merge(self, other, mergingFunction = None):
48+
if mergingFunction is None:
49+
mergingFunction = _defaultMergingFunction
50+
51+
for k in self._data.keys():
52+
v = self._data[k]
53+
ov = other._data[k]
54+
if isinstance(v, _ScalaMutableWrapper):
55+
v.merge(ov, mergingFunction)
56+
else:
57+
if mergingFunction(self._ctor, self._data, k, v, ov):
58+
pass
59+
else:
60+
if ov is not None:
61+
self._data[k] = ov
62+
63+
64+
def _defaultMergingFunction(objScalaClass, dataDict, k, v, ov) -> bool:
65+
return False
66+
67+
68+
class ScalaMutableWrapper(_ScalaMutableWrapper):
69+
__slots__ = ()
70+
71+
def _revertIter(self):
72+
return self._data.values()
73+
74+
def _revert(self):
75+
return self._ctor(*tuple(self._revertIter_()))
76+
77+
def __getattr__(self, k):
78+
return self._data[k]
79+
80+
def __setattr__(self, k, v):
81+
self._data[k] = v
82+
83+
def __dir__(self):
84+
return self._data.keys()
85+
86+
#def merge(self, other, mergingFunction = None):
87+
# raise NotImplementedError
88+
89+
90+
class ScalaCollectionMutableWrapper(_ScalaMutableWrapper):
91+
__slots__ = ()
92+
93+
def __init__(self, ji, o, template=None, ctor=None, data=None):
94+
super().__init__(ji, o, ctor=ji.scalaSeq, data=[ji.scalaWrapSomeKindOfImmutableObject(el) for el in ji.JavaConverters.asJavaCollection(o)])
95+
96+
def __getitem__(self, k):
97+
return self._data[k]
98+
99+
def __setitem__(self, k, v):
100+
self._data[k] = v
101+
102+
def __getattr__(self, k):
103+
return getattr(self._data, k)
104+
105+
def __setattr__(self, k, v):
106+
setattr(self._data, k, v)
107+
108+
def _revertIter(self):
109+
return self._data
110+
111+
def _revert(self):
112+
return self._ctor(list(self._revertIter_()))
113+
114+
def merge(self, other, mergingFunction = None):
115+
self.extend(other)
116+
117+
118+
119+
class ScalaJVMInitializer:
120+
__slots__ = ("ji", "scalaVersion")
121+
def __init__(self, classPathz: ClassPathT, classes2import: ClassesImportSpecT) -> None:
122+
self.__class__.ji.__set__(self, SelectedJVMInitializer(classPathz, classes2import))
123+
self.loadScala()
124+
125+
def __getattr__(self, k):
126+
return getattr(self.ji, k)
127+
128+
def __setattr__(self, k, v):
129+
setattr(self.ji, k, v)
130+
131+
def loadScala(self) -> None:
132+
self.ji.ImmutArraySeq = None
133+
self.loadClasses((
134+
("scala.util.Properties", "ScalaProps"),
135+
"scala.concurrent.Await",
136+
"scala.collection.Iterable",
137+
"scala.collection.mutable.Seq",
138+
"scala.collection.mutable.ListBuffer",
139+
("scala.collection.mutable.ArraySeq", "MutArraySeq"),
140+
("scala.collection.immutable.HashMap", "ImmutHashMap"),
141+
("scala.collection.mutable.HashMap", "MutHashMap"),
142+
"scala.collection.JavaConverters",
143+
"scala.Some",
144+
("scala.None", "none"),
145+
("scala.Predef$", "scalaPredef"),
146+
("scala.collection.Seq$", "scalaCollSeq"),
147+
"java.util.Arrays"
148+
))
149+
150+
self.scalaVersion = tuple(int(el) for el in str(self.ScalaProps.versionNumberString()).split("."))
151+
152+
if self.scalaVersion > (2, 13):
153+
self.loadClasses(
154+
("scala.collection.immmutable.ArraySeq", "ImmutArraySeq")
155+
)
156+
else:
157+
warnings.warn("Using mutable ArraySeq instead of immutable one, since immutable is not present in this version of Scala " + repr(self.scalaVersion))
158+
159+
self.scalaPredef = getattr(self.scalaPredef, "MODULE$")
160+
self.scalaCollSeq = getattr(self.scalaCollSeq, "MODULE$")
161+
162+
def getScalaSignatureAnnotation(self, scalaClass) -> typing.Any:
163+
return self.__class__.getScalaSignatureAnnotationFromReflectedClass(self.reflectClass(scalaClass))
164+
165+
@classmethod
166+
def getScalaSignatureAnnotationFromReflectedClass(cls, classRefl) -> typing.Any:
167+
for annot in classRefl.annotations:
168+
if annot.annotationType().name == "scala.reflect.ScalaSignature":
169+
return annot
170+
return None
171+
172+
def _ensureScalaSignatureBytesDecoderLazyLoaded(self):
173+
global decodeScalaSignature
174+
if decodeScalaSignature is None:
175+
try:
176+
from .scalaTransformArray import decode as decodeScalaSignaturePython
177+
178+
def decodeScalaSignature(s: bytes) -> bytes:
179+
s = bytearray(bytes(s))
180+
l = decodeScalaSignaturePython(s)
181+
return bytes(s[:l])
182+
183+
184+
except ImportError:
185+
ByteCodecs = ji.loadClass("scala.reflect.internal.pickling.ByteCodecs")
186+
187+
def decodeScalaSignature(s: bytes) -> bytes:
188+
l = ByteCodecs.decode(s)
189+
s = bytes(s)
190+
return s[:l]
191+
192+
def getScalaSignatureAnnotationBytes(self) -> bytes:
193+
self._ensureScalaSignatureBytesDecoderLazyLoaded()
194+
scalaSignAnnot = self.getScalaSignatureAnnotation(classRefl)
195+
if scalaSignAnnot:
196+
s = scalaSignAnnot.bytes().getBytes("UTF-8")
197+
return decodeScalaSignature(s)
198+
199+
def scalaMap(self, m, mutable=False):
200+
if mutable:
201+
ctor = self.MutHashMap
202+
else:
203+
ctor = self.ImmutHashMap
204+
205+
seq = ctor(len(m))
206+
for k, v in m.items():
207+
seq.update(k, v)
208+
return seq
209+
210+
def scalaArrSeq(self, it, mutable=True):
211+
it = list(it)
212+
if mutable or self.ImmutArraySeq is None:
213+
ctor = self.MutArraySeq
214+
else:
215+
ctor = self.ImmutArraySeq
216+
217+
seq = ctor(len(it))
218+
for k, v in enumerate(it):
219+
seq.update(k, v)
220+
return seq
221+
222+
def scalaSet(self, it, mutable=True):
223+
return self.scalaArrSeq(it, mutable=mutable).toSet()
224+
225+
def scalaSeq(self, it):
226+
coll = self.scalaCollSeq.apply(self.scalaPredef.wrapRefArray(list(it)))
227+
coll = coll.to(self.scalaCollSeq.canBuildFrom())
228+
return coll
229+
#return self.scalaCollSeq.apply(self.scalaPredef.wrapRefArray(list(it)))
230+
#return self.scalaPredef.wrapRefArray(list(it))
231+
#return self.JavaConverters.collectionAsScalaIterable(self.Arrays.asList(list(it))).toSeq()
232+
233+
scalaTupleRx = re.compile("^_(\\d+)$")
234+
235+
@classmethod
236+
def scalaDetuple(cls, t):
237+
res = [None] * t.productArity()
238+
for n in dir(t):
239+
m = cls.scalaTupleRx.match(n)
240+
if m is not None:
241+
res[int(m.group(1)) - 1] = getattr(t, n)()
242+
return tuple(res)
243+
244+
@classmethod
245+
def scalaDeOption(cls, o):
246+
if o.isEmpty():
247+
return None
248+
249+
return o.value()
250+
251+
@staticmethod
252+
def getSomeKindOfImmutableObjectTemplate(cls):
253+
c = max(cls.class_.getConstructors(), key=lambda ct: len(ct.getParameters()))
254+
return OrderedDict([(str(p.getName()), None) for p in c.getParameters()])
255+
256+
def scalaWrapSomeKindOfImmutableObject(self, o, template=None):
257+
if not isinstance(o, (str, self.String, int, float, bool, type(None), ScalaMutableWrapper, ScalaCollectionMutableWrapper)):
258+
#print(o.__class__, isinstance(o, self.Iterable), o.__class__.__mro__)
259+
if isinstance(o, self.Iterable):
260+
return ScalaCollectionMutableWrapper(self, o)
261+
else:
262+
if hasattr(o, "copy$default$1"):
263+
o = ScalaMutableWrapper(self, o)
264+
return o
265+
else:
266+
return o

0 commit comments

Comments
 (0)