closeio / flask-mongorest Goto Github PK
View Code? Open in Web Editor NEWRestful API framework wrapped around MongoEngine
License: Other
Restful API framework wrapped around MongoEngine
License: Other
I can only see docs
directory, but there is no link to generated docs. I found this, but it does not seem to be very much maintained.
I like the idea behind this project and I wanted to try it out, but I am not going to start with reading __init__.py
. There is README
, but it is rather brief, I would appreciate more elaborated docs about all the concepts presented.
as titled, I think it's better to make it init_app compatible.
Thanks
This blog post has a great discussion about hypermedia formats like HAL and Siren.
Personally, I'm quite interested in exploring these formats and supporting one or more of them in my API. The issue I see is that the current approach expects each dispatch_request
method to return a dict
and then it marshals that through mimerender
into either JSON or XML.
But the issue I see in supporting things like HAL or Siren is that these are effectively different content types (application/hal+json
and application/vnd.siren+json
, respectively). In both cases, you could get by with returning different dictionaries, but the structure of the dictionaries wouldn't be the same and it depends on the contents of the underlying Document. So mimerender
can't make this call, it has to come from something resource specific.
You can make something like this:
class HALResource(Resource):
serialize_embedded = True
def serialize_field(self, obj, **kwargs):
if self.serialize_embedded:
return self.serialize(obj, **kwargs)
else:
return self._url(str(obj.id))
def serialize(self, obj, **kwargs):
# Get the normal serialized version
rep = super(HALResource,self).serialize(obj, **kwargs)
# Pull the database ID out of this and then remove that field
myid = rep["id"]
rep.pop("id")
# Compute the URI for this resource (including host name)
myuri = self._url(str(myid))
# Populate the initial _links and _embedded field
links = {"self": myuri}
embedded = {}
# Added related resources to embedded if they have
# a uri_prefix
for k in self.related_resources:
r = self.related_resources[k]()
if r.uri_prefix!=None:
v = rep[k]
rep.pop(k)
embedded[k] = v
# Add special fields
rep["_links"] = links
if len(embedded)>0:
rep["_embedded"] = embedded
# Return the HAL version
return rep
But this links the Resource with the content type in an ugly way. What if you want to support both formats? It seems to me that what you need is to have the serialize
method handle this somehow. Ideally, it would be nice to have renderers for different formats, e.g.
class HALJSonRenderer(SerializeRenderer):
content_type = 'application/hal+json`
def serialize(obj, **kwargs):
...
class MyResource(Resource):
renderers = [DefaultJSONRenderer, DefaultXMLRender, HALJSonRenderer, HALXMLRenderer, SirenRenderer, JSONCollectionRenderer]
and then the Resource.serialize
method could simply look at the requested content type and call the appropriate renderer. The default value for renderers
should include at least [DefaultJSONRenderer, DefaultXMLRenderer]
(which would capture the current approach) but could also be extended to include other supported content types without any backward compatibility issues.
Does this seem like a reasonable approach? If so, I could take a shot at making a backward compatible pull request to add this functionality.
flask-mongorest should support CORS (Access-Control-Allow-Origin)
Flask has a snippet for this: http://flask.pocoo.org/snippets/56/
Validating a request containing a document that has a ListField(ListField()) fails
File "/Users/anemitz/Dropbox/projects/flask-mongorest/flask_mongorest/views.py", line 58, in post
self._resource.validate_request()
File "/Users/anemitz/Dropbox/projects/flask-mongorest/flask_mongorest/resources.py", line 191, in validate_request
json_data = json_to_form_data('', self.data)
File "/Users/anemitz/Dropbox/projects/flask-mongorest/flask_mongorest/resources.py", line 176, in json_to_form_data
form_data.update(json_to_form_data('%s%s-%d-' % (prefix, k, n), el))
File "/Users/anemitz/Dropbox/projects/flask-mongorest/flask_mongorest/resources.py", line 173, in json_to_form_data
for k, v in json_data.iteritems():
AttributeError: 'list' object has no attribute 'iteritems'
class FooResource(Resource):
form = FooForm
document = FooDocument
class BarResource(Resource):
document = BarDocument
related_resources = {
'foos': FooResource
}
In the above scenario, submitting a BarDocument with a list of Foo's should validate using the FooResource.form before saving.
I have created a custom mongoengine document field EnumField.
class MyDocument(Document):
my_enum = EnumField(MyEnum)
I also created a Resource and ResourceView for this class
class MyDocumentResource(Resource):
document = MyDocument
@api.register(name='my_documents', url='/api/my-documents/')
class MyDocumentView(ResourceView):
resource = MyDocumentResource
methods = [methods.Create, methods.Update, methods.Fetch, methods.List]
However, when I call GET /api/my-documents/
, I get the error:
unbound method default() must be called with JSONEncoder instance as first argument
This is caused because the JSONEncoder does not know how to encode an enum instance. I looked into the MongoEncoder
class, and noticed that I could add some custom logic there.
class MyMongoEncoder(MongoEncoder):
def default(self, value, **kwargs):
if isinstance(value, Enum):
return unicode(value.value)
return super(BaseMongoEncoder, self).default(value, **kwargs)
However, I couldn't easily override the MongoEncoder class because it's hard coded here.
I ended up copy-pasting ResourceView.dispatch_request into my own MyResourceView.dispatch_request and creating my own render_json method, but this isn't a very clean method of doing making this work. Is there a better way to do this? If not, there should possibly be a way to specify your own render_json method and/or custom encoder class.
FYI It looks like this issue is already resolved, but this feature would also provide a workaround for this issue.
Where is the from flask.ext.views.base import View
?
https://github.com/elasticsales/flask-mongorest/blob/master/flask_mongorest/views.py#L11
It has been a few years and people are still using this library, maybe time to push an update?
In my opinion it's a very bad default to not raise in handle_serialization_error
, and makes it difficult to debug issues unrelated (and related) to serialization (e.g. if get_fields()
raises an exception).
The debug-template couldn't be found by the application, because the folder won't be "installed" by the setup.py
Hey there,
I have written the following MongoDB schema to return required data, notice the use of a projection on adducts.positive.peaks.
db.metabolites.find(
{ "adducts.positive.peaks.accurate_mass": {$gt : 1200, $lt : 1220}},
{ "name" : 1, "accurate_mass" :1, "adducts.positive.peaks.$": 1}
)
However, there doesn't seem to be any clear way of doing this in flask-mongorest.
Are there any plans to implement the $
operator in flask-mongorest?
Thank you,
Keiron.
Maybe i didn't find it. Is it planned?
Trying to implement a reporting API for multiple mongo databases with the same structure using mongorest...
Have tried to implement this using the mongoengine connect mechanism:
for mongoconfig in configmongos:
print "Connecting: "+mongoconfig["name"]
db.connect(
name = mongoconfig["name"],
host = mongoconfig["host"],
port = mongoconfig["port"],
db = mongoconfig["database"]
)
and then using a variable in my document class:
class Products(db.Document):
productName = db.StringField()
businessUnit = db.StringField()
brand = db.StringField()
subBrand = db.StringField()
franchise = db.StringField()
category = db.StringField()
subCategory = db.StringField()
meta = {'collection': 'products',"db_alias": selectedInstance}
But it seams that the db alias is always "default"
Any way to implement this?
Thus making us more consistent with the approach recommended at http://flask.pocoo.org/docs/0.10/extensiondev/#the-extension-code
We should be able to enable the API in two ways:
MongoRest(app)
(already supported).api = Mongorest()
-> app creation (e.g. app = create_app('the-config.cfg')
) -> api.init_app(app)
.In the 1st case, MongoRest
's __init__
should call init_app
.
See #55 for a proposed solution that unfortunately never made it to the master.
"""
File "/home/ubuntu/closeio/venv/src/flask-mongorest/flask_mongorest/views.py", line 62, in post
obj = self._resource.create_object()
File "/home/ubuntu/closeio/current/closeio/app/resources.py", line 560, in create_object
lead = super(LeadResource, self).create_object(**kwargs)
File "/home/ubuntu/closeio/venv/src/flask-mongorest/flask_mongorest/resources.py", line 474, in create_object
self._save(obj)
File "/home/ubuntu/closeio/venv/src/flask-mongorest/flask_mongorest/resources.py", line 458, in _save
raise ValidationError({'field-errors': serialize_errors(e.errors)})
File "/home/ubuntu/closeio/venv/src/flask-mongorest/flask_mongorest/resources.py", line 455, in serialize_errors
return dict((k, serialize_errors(v)) for (k, v) in errors.iteritems())
File "/home/ubuntu/closeio/venv/src/flask-mongorest/flask_mongorest/resources.py", line 455, in
return dict((k, serialize_errors(v)) for (k, v) in errors.iteritems())
File "/home/ubuntu/closeio/venv/src/flask-mongorest/flask_mongorest/resources.py", line 457, in serialize_errors
return str(errors)
UnicodeEncodeError: 'ascii' codec can't encode character u'\u0329' in position 43: ordinal not in range(128)
"""
This really should be the last one(!)
I'm currently trying to write an operator that will filter using the second variable in a ListField.
Given the example:
{
"adduct_weights": {
"negative": {
"count": 2,
"peaks": [["a", 135.123],["b", 136.123] ]
},
"neutral": 136.1252005136,
"positive": {
"count": 0,
"peaks": []
}
},
"id": "586ea4419c4fa6524867693f",
"name": "(+)-a-Pinene"
},
I'd like to filter by the second item in each item in the peaks
list for negative
for a value.
I've written the following operator, which doesn't retrieve any data.
class IonisationPpm(Operator):
op = "ppm"
def prepare_queryset_kwargs(self, field, value, negate=False):
if value == None:
value = ["negative", 100, 10]
else:
value = [x for x in value.split(",")]
ionisation = value[0]
mz, ppm_threshold = [float(x) for x in value[1:]]
print mz, ppm_threshold
difference = abs(mz * (ppm_threshold * 0.0001)) # PPM to diff.
return {
field + "__" + value[0] + "__count__gt": 0,
field + "__" + value[0] + "__peaks__1__gt": mz - difference,
field + "__" + value[0] + "__peaks__1__lt": mz + difference
}
Looking at this hasn't helped!
Cleanup was started (and merged) in #62 but there is more todo. Some candidates:
/api/v1/lead/?_limit=1
returns 2 result
/api/v1/lead/?_limit=0
returns 1 result
Note that it needs to fetch one more result for the has_more field. It just shouldn't return it.
Hi,
I am interested in extending flask-mongorest to expose information about the mongoengine objects and associated mongorest resources via the API. What would you suggest is the best way of doing so? Should this be done via flask-mongorest or cleancat?
Thanks!
Hi,
Cool project! I notice sphinx is a dependency - is there a documentation website or is the readme it?
Thanks!
Hey there,
I'm new to MongoDB and I would like to know how I can access an embedded document using flask-mongorest. I know how to do it in the cli, but I can't seem to find documentation here.
Given an output of...
"data": [
{
"adducts": {
"Anion": {
"[M-H]1-": [
[
349.2093240735,
100.0
],
[
350.2126789113,
21.631456585464488
]
]
},
"Canion": {},
"Nominal": [
[
350.2093240735,
100.0
],
[
351.2126789113,
21.631456585464488
]
]
},
"id": "586bf20b9f0029837dfc9d39",
"molecular_formula": "C20H30O5",
"name": "Oryzalic acid B",
"origins": [
"Endogenous",
"Food"
]
}...
I'd like to filter out anything that has an "anion" from "adducts" from a given value compared to the first element the first list in that given key.
Is this possible in flask-mongorest?
Thanks,
Keiron.
How are file fields dealt with in flask-mongorest? I get the following when trying to retrieve one:
TypeError: unbound method default() must be called with JSONEncoder instance as first argument (got GridFSProxy instance instead)
File "/usr/local/lib/python2.6/dist-packages/flask/app.py", line 1701, in call
return self.wsgi_app(environ, start_response)
File "/usr/local/lib/python2.6/dist-packages/flask/app.py", line 1689, in wsgi_app
response = self.make_response(self.handle_exception(e))
File "/usr/local/lib/python2.6/dist-packages/flask/app.py", line 1687, in wsgi_app
response = self.full_dispatch_request()
File "/usr/local/lib/python2.6/dist-packages/flask/app.py", line 1360, in full_dispatch_request
rv = self.handle_user_exception(e)
File "/usr/local/lib/python2.6/dist-packages/flask/app.py", line 1358, in full_dispatch_request
rv = self.dispatch_request()
File "/usr/local/lib/python2.6/dist-packages/flask/app.py", line 1344, in dispatch_request
return self.view_functionsrule.endpoint
File "/usr/local/lib/python2.6/dist-packages/flask/views.py", line 83, in view
return self.dispatch_request(_args, _kwargs)
File "/usr/local/lib/python2.6/dist-packages/mimerender.py", line 246, in wrapper
content = renderer(_result)
File "/usr/local/lib/python2.6/dist-packages/Flask_MongoRest-0.1.1-py2.6.egg/flask_mongorest/views.py", line 15, in
render_html = lambda *_payload: render_template('mongorest/debug.html', data=json.dumps(payload, cls=MongoEncoder, sort_keys=True, indent=4))
File "/usr/lib/python2.6/json/init.py", line 237, in dumps
*_kw).encode(obj)
File "/usr/lib/python2.6/json/encoder.py", line 367, in encode
chunks = list(self.iterencode(o))
File "/usr/lib/python2.6/json/encoder.py", line 309, in _iterencode
for chunk in self._iterencode_dict(o, markers):
File "/usr/lib/python2.6/json/encoder.py", line 275, in _iterencode_dict
for chunk in self._iterencode(value, markers):
File "/usr/lib/python2.6/json/encoder.py", line 306, in _iterencode
for chunk in self._iterencode_list(o, markers):
File "/usr/lib/python2.6/json/encoder.py", line 204, in _iterencode_list
for chunk in self._iterencode(value, markers):
File "/usr/lib/python2.6/json/encoder.py", line 309, in _iterencode
for chunk in self._iterencode_dict(o, markers):
File "/usr/lib/python2.6/json/encoder.py", line 275, in _iterencode_dict
for chunk in self._iterencode(value, markers):
File "/usr/lib/python2.6/json/encoder.py", line 317, in _iterencode
for chunk in self._iterencode_default(o, markers):
File "/usr/lib/python2.6/json/encoder.py", line 323, in _iterencode_default
newobj = self.default(o)
File "/usr/local/lib/python2.6/dist-packages/Flask_MongoRest-0.1.1-py2.6.egg/flask_mongorest/utils.py", line 22, in default
return json.JSONEncoder.default(value, *_kwargs)
Following up from #103, I am experiencing an issue involving the use of an EmbeddedDocument.
My MongoDB collection currently resembles the following:
[
{
"accurate_mass": 350.45000749099137,
"smiles": "CC(C)(C1CCC23CC(CCC2C1(C)CC(O)=O)C(=C)C3O)C(O)=O",
"isotopic_distributions": [
[
0.0,
100.0
],
[
1.003354837799975,
21.631456585464488
]
],
"name": "Oryzalic acid B",
"origins": [
"Endogenous",
"Food"
],
"molecular_formula": "C20H30O5",
"adduct_weights": {
"positive": {
"count": 0,
"peaks": []
},
"neutral": 350.2093240735,
"negative": {
"count": 1,
"peaks": [
[
"[M-H]1-",
349.2093240735
]
]
}
}
},...
]
If you look at the adduct_weights
key, it holds a collection resembling:
"adduct_weights": {
"positive": {
"count": 0,
"peaks": []
},
"neutral": 350.2093240735,
"negative": {
"count": 1,
"peaks": [
[
"[M-H]1-",
349.2093240735
]
]
}
Following the example provided within this repository, I have written the following Documents and Resources.
class NegativeAdduct(db.EmbeddedDocument):
count = db.IntField()
peaks = db.ListField(db.ListField(db.DynamicField()))
class PositiveAdduct(db.EmbeddedDocument):
count = db.IntField()
peaks = db.ListField(db.ListField(db.DynamicField()))
class AdductWeights(db.EmbeddedDocument):
neutral = db.FloatField()
negative = db.EmbeddedDocumentField(NegativeAdduct)
positive = db.EmbeddedDocumentField(PositiveAdduct)
class AdductWeightsResource(Resource):
document = AdductWeights
class MetaboliteAdduct(db.DynamicDocument):
meta = {"collection": "metabolites"}
name = db.StringField()
accurate_mass = db.FloatField()
smiles = db.StringField()
isotopic_distributions = db.StringField()
molecular_formula = db.StringField()
origins = db.ListField(db.StringField())
adduct_weights = db.EmbeddedDocumentField(AdductWeights)
class MetaboliteAdductResource(Resource):
document = MetaboliteAdduct
filters = {
"name" : [ops.Contains, ops.Startswith, ops.Exact],
}
related_resources = {
"adduct_weights" : AdductWeightsResource
}
@api.register(name="adductsapi", url="/api/adducts/")
class MetaboliteAdductView(ResourceView):
resource = MetaboliteAdductResource
methods = [methods.List, methods.Fetch]
No error is being thrown when I query MetaboliteAdductView
's url, however no data is being returned either.
{
"data": [],
"has_more": true
}
Where have I gone wrong here?
I am a novice, have some problems.
For dynamically add fields, I use DynamicDocument in doucument.py.
Right now there's validate_request
which isn't really supposed to be used for authorization-related tasks (since it's not called by GET/DELETE), and there's view-level authentication_methods
. And there's get_queryset
, which doesn't really have access to the method type (update/fetch/etc.)
No single obvious way to enforce that some users should be able to GET certain items, but others should be able to PUT/DELETE them
Should this be handled at the view or resource level?
Basically i have some other portions of the rest api that don't use mongoengine and i want to keep them together in 1 blueprint.
Hi, I thought mongodB is schemaless? May I ask what is the use of schemas in this case? Thanks
Hey there,
I have written the following code to return all documents in my collection.
class GetAll(Operator):
op = "test
def apply(self, queryset, field, value, negate=False):
collection = MetaboliteFull._get_collection().find({})
print collection.explain()
print collection.count()
return collection
Which returns...
{
"data": [],
"has_more": false
}
When I look at the query using the flask-debugtoolbar tool nothing obvious is given.
The output from the prints are...
{u'executionStats': {u'executionTimeMillis': 0, u'nReturned': 495, u'totalKeysExamined': 0, u'allPlansExecution': [], u'executionSuccess': True, u'executionStages': {u'needYield': 0, u'direction': u'forward', u'saveState': 3, u'restoreState': 3, u'isEOF': 1, u'docsExamined': 495, u'nReturned': 495, u'needTime': 1, u'filter': {u'$and': []}, u'executionTimeMillisEstimate': 0, u'invalidates': 0, u'works': 497, u'advanced': 495, u'stage': u'COLLSCAN'}, u'totalDocsExamined': 495}, u'queryPlanner': {u'parsedQuery': {u'$and': []}, u'rejectedPlans': [], u'namespace': u'dimedb.metabolites', u'winningPlan': {u'filter': {u'$and': []}, u'direction': u'forward', u'stage': u'COLLSCAN'}, u'indexFilterSet': False, u'plannerVersion': 1}, u'ok': 1.0, u'serverInfo': {u'host': u'think-big', u'version': u'3.2.12', u'port': 27017, u'gitVersion': u'ef3e1bc78e997f0d9f22f45aeb1d8e3b6ac14a14'}}
495
Is there something I'm missing?
There are a couple of except Exception, e:
in views.py and that syntax is incompatible with python 3. A simple change to except Exception as e:
should solve the issue.
When running the sample app with the sample curl POST I am getting the following exception:
ValidationError: author_id_from_a_previous_api_call is not a valid ObjectId
This seems to be failing on retrieving the document that was just posted, but I can confirm the document never gets inserted into Mongo. I am a loss for how to track down where the insert is failing.
Here are my installed dependencies:
Flask==0.9
Flask-MongoRest==0.1.1
Flask-Views==0.2.1
Flask-WTF==0.8.2
Jinja2==2.6
WTForms==1.0.3
Werkzeug==0.8.3
argparse==1.2.1
distribute==0.6.24
flask-mongoengine==0.6
mimerender==0.5.1
mongoengine==0.7.9
pymongo==2.4.2
python-dateutil==2.1
python-mimeparse==0.1.4
six==1.2.0
wsgiref==0.1.2
and I'm using Mongo version 2.0.6 with Python 2.7.3. Full stack trace is here:
Any help would be greatly appreciated.
Thank you!
In our use case we would like to filter out documents from a defined resource (do not return documents that have been logically deleted).
How would this be done with mongorest? Using a signal perhaps?
It's been nearly a year?
Hello I've forked the project and I'm trying to update the syntax and dependencies to support the latest versions of python. I'm kinda stuck at mongoengine since a forked version is being used. Is there any way i could get the differences between the two or do i have to stick to the forked version.
It would be good to update pip. last update seems to be 2012 https://pypi.python.org/pypi/Flask-MongoRest/0.1.1
Maybe I'm missing something, but I think there is a fundamental issue in MongoRest.
I created a super simple example to demonstrate the issue here: https://gist.github.com/mtiller/4961630
If I run this application and then create an author as follows:
% curl -H "Content-Type: application/json" -X POST -d '{"name": "Douglas Adams"}' http://localhost:5000/authors/
It creates an author, but the response looks like this:
{"name": "Douglas Adams", "id": "511e66731d41c8718c196708"}
The problem I see here is that this is not returning a URI. The "Uniform Interface" constraint for REST says that resources should be named. In this case, the resources name is, in fact, /authors/511e66731d41c8718c196708/ (which I figured out by trial and error). But a POST should return to the URI (resource), not the representation. If I had done this:
% curl http://localhost:5000/authors/511e66731d41c8718c196708/
THEN, I get:
{"name": "Douglas Adams", "id": "511e66731d41c8718c196708"}
...which is correct since this is a JSON representation.
But the problem goes deeper than just POST responses. If I then want to create a Book object I should be using the RESOURCE not the representation, e.g.
curl -H "Content-Type: application/json" -X POST -d '{"title": "Hitchhikers Guide to the Galaxy", "author": "/authors/511e66731d41c8718c196708/"}' http://localhost:5000/books/
However, this fails with:
{"field-errors": {"name": "Field is required"}}
It turns out what is required is this:
% curl -H "Content-Type: application/json" -X POST -d '{"title": "Hitchhikers Guide to the Galaxy", "author": {"name": "Douglas Adams", "id": "511e66731d41c8718c196708"}}' http://localhost:5000/books/
Note that I had to put the REPRESENTATION in for the author, not the resource.
Am I missing something here? This seems like a significantly violation of REST principles. If I remove the 'related_resources' setting, it gets slightly better because then it requires this:
% curl -H "Content-Type: application/json" -X POST -d '{"title": "Hitchhikers Guide to the Galaxy", "author": "511e66731d41c8718c196708"}' http://localhost:5000/books/
...and you get back...
{"title": "Hitchhikers Guide to the Galaxy", "id": "511e6bb61d41c8723fba687c", "author": "511e66731d41c8718c196708"}
So at least now we are giving and getting a resource identifier (although it isn't technically a URI). But it is still inconsistent with what is returned by the POST method used to create the author. In other words, as a developer using such an API I have to understand how to turn the representation (from POST) into a resource identifier which I should not have to do.
Or am I missing something?
I would like to add custom validation to some fields of the document (and optionally return error), but I don't know what methods should I override (Resource.create_object or ResourceView.post?). It's not just validation, I'm looking for a way how to run custom code in POST requests. Is this even possible? Thanks!
curl -XPOST "http://localhost:5000/user/" -d '{"name": "anthony"}'
currently returns an Invalid json error unless the Content-Type header is explicitly set.
When I send a POST request to an url without ended in slash (f.e /user), it redirects me to the same url ended with the slash (/user/) but with a GET instead of a POST method.
Could you please give me a solution for this issue?
Thanks.
hi, i need some help
i want to use JWT as authentication and i'm trying to use Flask-Jwt-Extented that using jwt_required decorator to protect resource.
My question is how to implement this decorator to resource?
I am trying to implement flask-mongorest in my project. So far, it works really nice. Thanks for the hard work on this project.
Now, I would like to build more complex Rest uri's like
/user/(int: user_id)/article/(int: article_id)/(read)
Where for user (int: user_id) I can tag article (int: article_id) as read.
The example code only gives examples like /user/(int: user_id). Is the uri I am trying to build possible? Could you give me some hints how to implement this?
Thanks!
File "/home/osboxes/anaconda/envs/venv/lib/python2.7/site-packages/flask/exthook.py", line 87, in load_module
raise ImportError('No module named %s' % fullname)
ImportError: No module named flask.ext.views
The other imports are fine:
from flask_mongorest.resources import Resource
from flask_mongorest import operators as ops
from flask_mongorest import methods
class MyResource(Resource):
rename_fields = {
'test': 'test_id'
}
{u'field-errors': {u'test': [u'Not a valid choice']}}
The DocumentProxy class is now in resources.py, which requires the elasticsales fork of mongoengine, is this intentional?
A declarative, efficient, and flexible JavaScript library for building user interfaces.
๐ Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. ๐๐๐
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google โค๏ธ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.