Code Monkey home page Code Monkey logo

thingweb-directory's Introduction

thingweb-directory's People

Contributors

6d77 avatar aparna-thuluva avatar aparnathuluva avatar danicic avatar egekorkan avatar h0ru5 avatar sharadasowmya14 avatar vcharpenay avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

thingweb-directory's Issues

out of memory error:java heapspace

The following was returned when trying to delete a TD:

<html>
<head>
<meta http-equiv="Content-Type" content="text/html;charset=ISO-8859-1"/>
<title>Error 500 </title>
</head>
<body>
<h2>HTTP ERROR: 500</h2>
<p>Problem accessing /td/c99c005e. Reason:
<pre>    org.eclipse.rdf4j.repository.RepositoryException: org.eclipse.rdf4j.sail.SailException: java.lang.OutOfMemoryError: Java heap space</pre></p>
<hr /><a href="http://eclipse.org/jetty">Powered by Jetty:// 9.3.6.v20151106</a><hr/>
</body>
</html>

Version 10 always gives 500 error

After installing the binary release following the instructions, localhost:8080 always gives a 500 error. Here is an example (all other URLs give the same response);

HTTP ERROR: 500
Problem accessing /api.json. Reason:

javax.servlet.http.HttpServletRequest.isAsyncStarted()Z

Powered by Jetty://

The TD in the 'Samples' folders are wrong

The TDs in the samples folder are not defined as in the Web Description document (https://w3c.github.io/wot-thing-description/):
Both of the following files defined a "metadata" object that is not defined anywhere in the standard document:
thingweb-directory/src/main/resources/samples/ledActuatorTD.jsonld
thingweb-directory/src/main/resources/samples/fan.jsonld

Besides, the "ledActuatorTD.jsonld" file should include its interactions inside an "interaction" array.

groovy.lang.MissingPropertyException: No such property: @id for class: java.lang.String

After registering the following TD with a successful "Created" response, the lookup as well as the direct URI under /td/ returns a groovy.lang.MissingPropertyException: No such property: @id for class: java.lang.String 500 error.

TD:

{
    "id": "urn:dev:wot:siemens:unicorn",
    "name": "Unicorn",
    "@context": "https://w3c.github.io/wot/w3c-wot-td-context.jsonld",
    "@type": "Thing",
    "security": [ ],
    "properties": {
        "brightness": {
            "type": "integer",
            "minimum": 0,
            "maximum": 255,
            "writable": true,
            "forms": [
                {
                    "href": "http://192.168.1.23:8080/Unicorn/properties/brightness",
                    "mediaType": "application/json"
                },
                {
                    "href": "coap://192.168.1.23:5683/Unicorn/properties/brightness",
                    "mediaType": "application/json"
                }
            ]
        },
        "color": {
            "type": "object",
            "properties": {
                "r": {
                    "type": "integer",
                    "minimum": 0,
                    "maximum": 255
                },
                "g": {
                    "type": "integer",
                    "minimum": 0,
                    "maximum": 255
                },
                "b": {
                    "type": "integer",
                    "minimum": 0,
                    "maximum": 255
                }
            },
            "writable": true,
            "forms": [
                {
                    "href": "http://192.168.1.23:8080/Unicorn/properties/color",
                    "mediaType": "application/json"
                },
                {
                    "href": "coap://192.168.1.23:5683/Unicorn/properties/color",
                    "mediaType": "application/json"
                }
            ]
        }
    },
    "actions": {
        "gradient": {
            "input": {
                "type": "array",
                "items": {
                    "type": "object",
                    "properties": {
                        "r": {
                            "type": "integer",
                            "minimum": 0,
                            "maximum": 255
                        },
                        "g": {
                            "type": "integer",
                            "minimum": 0,
                            "maximum": 255
                        },
                        "b": {
                            "type": "integer",
                            "minimum": 0,
                            "maximum": 255
                        }
                    }
                },
                "minItems": 2
            },
            "forms": [
                {
                    "href": "http://192.168.1.23:8080/Unicorn/actions/gradient",
                    "mediaType": "application/json"
                },
                {
                    "href": "coap://192.168.1.23:5683/Unicorn/actions/gradient",
                    "mediaType": "application/json"
                }
            ]
        },
        "forceColor": {
            "input": {
                "type": "object",
                "properties": {
                    "r": {
                        "type": "integer",
                        "minimum": 0,
                        "maximum": 255
                    },
                    "g": {
                        "type": "integer",
                        "minimum": 0,
                        "maximum": 255
                    },
                    "b": {
                        "type": "integer",
                        "minimum": 0,
                        "maximum": 255
                    }
                }
            },
            "forms": [
                {
                    "href": "http://192.168.1.23:8080/Unicorn/actions/forceColor",
                    "mediaType": "application/json"
                },
                {
                    "href": "coap://192.168.1.23:5683/Unicorn/actions/forceColor",
                    "mediaType": "application/json"
                }
            ]
        },
        "cancel": {
            "forms": [
                {
                    "href": "http://192.168.1.23:8080/Unicorn/actions/cancel",
                    "mediaType": "application/json"
                },
                {
                    "href": "coap://192.168.1.23:5683/Unicorn/actions/cancel",
                    "mediaType": "application/json"
                }
            ]
        }
    },
    "events": { },
    "links": [ ]
}

URI Decode for Displayed Links

Thing IDs often use URIs/URNs. When displaying them as the link to their TD, the URI should be decoded to get rid of percent encoding (urn%3A...).

SPARQL graph pattern examples/hints/docs missing

The semantic look-up query uses graph patterns, but there are no good examples on how to achieve intended results.

Please provide examples and links on how to use.

The lack of documentation renders the feature unusable for many, hence bug level issue.

Listing TDs gives 405 ERROR - version 10

I created Postman client based on Swagger documentation (api.json file) and tried to list available things (expecting empty list) and I got 405 ERROR.

(I set up version 10 according to this guideline #33)

Starting command needs to be more specific

The startup command as given does not work. It can't find the JAR file, and even if you are in the same directory as the JAR file (it's hidden down under build/libs) you need a version number. From the directory where I ran "gradle build", I used the following command to start the server:

java -jar build/libs/thingweb-directory*.jar `pwd`

Provide option to disable CoAP and/or HTTP interface

Maybe (eg for security reasons) I don't want to run the service over CoAP, or over HTTP (eg just one of the two). There should be a documented way to disable each interface (perhaps by assigning a port of 0).

A workaround exists: run inside a firewall and block those ports. But it would be better to have the option to not start them at the source in the first place.

Note as well that if HTTPS (or CoAPS) is added, I may still want to run an HTTP or CoAP interface in parallel. The reason is that I may have local processes running on the same computer (eg inside the firewall) and don't want to have to fuss with certificates etc (which may be broken anyway in the case the device is temporarily offline). In this case I might open the HTTPS port to the outside but block the HTTP port using the firewall so it is only accessible to internal processes. I might also do this on a local network and block external access to HTTP using the NAT firewall.

So in the long run the system may have four separate network interfaces (CoAP, CoAPS, HTTP, HTTPS) and I would like to selectively enable and disable each one.

Proposed feature: return list of TDs instead of full TD

Currently the search APIs always return the full TD for each result. This could be a lot, especially when performing a full list.

It would be very useful (even for the default Web UI) to have some means to return a list of Things only together with the links to retrieve the full TDs.

FrameFilterTest fails

gradle build fails (checkout from git of version 10.0.0) with the following output:

Task :directory-core:test

org.eclipse.thingweb.directory.rdf.FrameFilterTest > testFilter FAILED
java.lang.AssertionError at FrameFilterTest.groovy:25

21 tests completed, 1 failed, 3 skipped

Task :directory-core:test FAILED

FAILURE: Build failed with an exception.

  • What went wrong:
    Execution failed for task ':directory-core:test'.

There were failing tests. See the report at: file:///home/mmccool/Devel/thingweb-directory/directory-core/build/reports/tests/test/index.html

TDs polluted with blank node `@id`s...

The TD returned is quite polluted with useless blank node @ids... could be prettier.

{
    "@id": "_:b0",
    "@type": "Thing",
    "interaction": {
        "@id": "_:b1",
        "@type": "Property",
        "form": {
            "@id": "_:b2",
            "href": "coap://x.x.x.x/3303/0/5700",
            "td:mediaType": "text/plain"
        },
        "td:name": "temperature",
        "observable": "true",
        "schema": {
            "@id": "_:b3",
            "type": "string"
        },
        "writable": "false"
    },
    "td:name": "LwM2MWoTThing"
}

Support HTTPS and related options

Support (or document them if they already exist) options use HTTPS. This should also support specifying the path to and the names of the certificate and private key files (rather than using fixed names and locations, since they have to be managed by a different subsystem for renewal, eg certbot, and be shared by multiple web services).

There should also be options to support CoAPS, or disable CoAP, or disable HTTP.
It would also be handy to be able to choose the ports used.

Returning always URI Path when registering TDs in the system

Hi,

The issue is about registering TDs in the ThingWeb directory. Right now, if the TD is already registered, the operation returns a 400 response code. However, the operation does not return the URI path in this case.
In the particular case that a different node registers the same TD, the node will know that the TD is in the system but it won’t be able to access it (or modified it) since it does not know its URI path.

Thus, I would expect a 400 response code in CoAP with the URI path included. Likewise in HTTP.

Oscar

TD fields such as "name" or "rel" serialized wrongly with "td:" prefix

A TD registered with correct name fields becomes

{

    "@id": "_:b0",
    "@type": "Thing",
    "interaction": {
        "@id": "_:b1",
        "@type": "Property",
        "form": {
            "@id": "_:b2",
            "href": "coap://x.x.x.x/3303/0/5700",
            "td:mediaType": "text/plain"
        },
        "td:name": "temperature",
        "observable": "true",
        "schema": {
            "@id": "_:b3",
            "type": "string"
        },
        "writable": "false"
    },
    "td:name": "LwM2MWoTThing"

}

For some reason, the name is prefixed with td:.

The registered TD spec example contains:

"td:mediaType": "application/json",
"td:rel": [
    "readProperty",
    "writeProperty"
]

Starting the batch file directory-app.bat give error

On Windows 10 machine with Java 8 installed, starting the batch file of the release delivery results in error "Input string too long". A workaround for this is to use wildcarded classpath specification: set CLASSPATH=%APP_HOME%\lib*

Retrieving a deleted TD causes either a NullPointerException or an empty payload to be returned

If accepted content type is an RDF format, an empty payload is returned.

See stack trace when accepted content type is application/td+json:

java.lang.NullPointerException
	at com.github.jsonldjava.core.JsonLdApi.filterNodes(JsonLdApi.java:1697)
	at com.github.jsonldjava.core.JsonLdApi.frame(JsonLdApi.java:1402)
	at com.github.jsonldjava.core.JsonLdApi.frame(JsonLdApi.java:1353)
	at com.github.jsonldjava.core.JsonLdProcessor.frame(JsonLdProcessor.java:330)
	at com.github.jsonldjava.core.JsonLdProcessor$frame.call(Unknown Source)
	at org.eclipse.thingweb.directory.rdf.TDSerializer.writeContent(TDSerializer.groovy:113)
	at org.eclipse.thingweb.directory.ResourceSerializer$writeContent$0.call(Unknown Source)
	at org.eclipse.thingweb.directory.ResourceManager.get(ResourceManager.groovy:146)
	at org.eclipse.thingweb.directory.servlet.RegistrationHandleServlet.doGet(RegistrationHandleServlet.java:57)
	at javax.servlet.http.HttpServlet.service(HttpServlet.java:687)
	at javax.servlet.http.HttpServlet.service(HttpServlet.java:790)
	at org.eclipse.jetty.servlet.ServletHolder.handle(ServletHolder.java:812)
	at org.eclipse.jetty.servlet.ServletHandler$CachedChain.doFilter(ServletHandler.java:1669)
	at org.eclipse.thingweb.directory.filter.ContentNegotiationFilter.doFilter(ContentNegotiationFilter.java:127)
	at org.eclipse.jetty.servlet.ServletHandler$CachedChain.doFilter(ServletHandler.java:1652)
	at org.eclipse.jetty.servlet.ServletHandler.doHandle(ServletHandler.java:585)
	at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:143)
	at org.eclipse.jetty.security.SecurityHandler.handle(SecurityHandler.java:577)
	at org.eclipse.jetty.server.session.SessionHandler.doHandle(SessionHandler.java:223)
	at org.eclipse.jetty.server.handler.ContextHandler.doHandle(ContextHandler.java:1127)
	at org.eclipse.jetty.servlet.ServletHandler.doScope(ServletHandler.java:515)
	at org.eclipse.jetty.server.session.SessionHandler.doScope(SessionHandler.java:185)
	at org.eclipse.jetty.server.handler.ContextHandler.doScope(ContextHandler.java:1061)
	at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:141)
	at org.eclipse.jetty.server.handler.HandlerWrapper.handle(HandlerWrapper.java:97)
	at org.eclipse.jetty.server.Server.handle(Server.java:499)
	at org.eclipse.jetty.server.HttpChannel.handle(HttpChannel.java:311)
	at org.eclipse.jetty.server.HttpConnection.onFillable(HttpConnection.java:258)
	at org.eclipse.jetty.io.AbstractConnection$2.run(AbstractConnection.java:544)
	at org.eclipse.jetty.util.thread.QueuedThreadPool.runJob(QueuedThreadPool.java:635)
	at org.eclipse.jetty.util.thread.QueuedThreadPool$3.run(QueuedThreadPool.java:555)
	at java.lang.Thread.run(Thread.java:745)

PUT method not supported via HTTP

When trying to update (using PUT) a TD previously created with POST via the HTTP interface, the following error is received. I am getting this with my OCF metadata bridge, where I want to update TDs "in place". As a workaround for now I will use POST/DELETE in place of PUT, but this is inelegant (and is not exactly equivalent, as it also changes the keys to the entry in the Thing Directory...).

PUT does seem to work through CoAP, so this may be a HTTP/CoAP bridge issue.

WOT-OCF-GEN-DEBUG 11409: Status: 405
WOT-OCF-GEN-DEBUG 11409: Headers: {"date":"Sun, 05 Nov 2017 22:35:45 GMT","cache-control":"must-revalidate,no-cache,no-store","content-type":"text/html;charset=iso-8859-1","content-length":"361","connection":"close","server":"Jetty(9.3.z-SNAPSHOT)"}
WOT-OCF-GEN-DEBUG 11409: Thing Directory PUT Response: 405
WOT-OCF-GEN-DEBUG 11409: Error updating TD Intel-OCF-fb6481e0-79e1-4be0-99c1-df9bcbb898a0
Body:

<title>Error 405 </title>

HTTP ERROR: 405

Problem accessing /td/a45b5e29. Reason:

    HTTP method PUT is not supported by this URL


Powered by Jetty:// 9.3.z-SNAPSHOT

Document Build Process completely

Be explicit for us non-Java users (I had to go dig through a gradle tutorial to find out the following):

gradle build

It would also be good to document requirements, specifically the minimum version of Java needed, whether OpenJDK works, etc.

Uploading a valid TD -> Error 500: could not parse JSON-LD

I've downloaded and started directory 0.9.0.
When upload a JSON (with type JSON-LD) the upload is succesfull.

When uploading a JSON-LD (from Thing Description specification draft Example 2 from 24. January 2019). The TD is valid, regarding thingweb playground, which is using the TD specification from 17. January 2019
{ "@context": [ "http://www.w3.org/ns/td", {"http": "http://www.w3.org/2011/http#"} ], "id": "urn:dev:wot:com:example:servient:lamp", "name": "MyLampThing", "securityDefinitions": {"basic_sc": { "scheme": "basic", "in": "header" }}, "security": ["basic_sc"], "properties": { "status": { "readOnly": false, "writeOnly": false, "observable": false, "type": "string", "forms": [{ "href": "https://mylamp.example.com/status", "http:methodName": "GET", "contentType": "application/json" }] } }, "actions": { "toggle": { "idempotent": false, "safe": false, "forms": [{ "href": "https://mylamp.example.com/toggle", "http:methodName": "POST", "contentType": "application/json" }] } }, "events": { "overheating": { "data": {"type": "string"}, "forms": [{ "href": "https://mylamp.example.com/oh", "subprotocol": "longpoll", "contentType": "application/json" }] } } }

I'm getting this error:
javax.servlet.ServletException: org.eclipse.rdf4j.rio.RDFParseException: Could not parse JSONLD

DELETE Method in HTTP does not update global list

After using DELETE on a previously created TD seems to delete it from the database as the direct URL no longer works. However, if you ask for ALL the TDs using the /td root URL, the deleted TD is still shown. This seems to happen only with the HTTP interface (we checked under CoAP and the deleted TDs are NOT listed) so it's probably a caching issue (e.g. the CoAP/HTTP proxy is incorrectly caching the overall TD list).

Error in function TDLookUpEPHandler.java

Hi guys,

There is an error in the function named 'get' in the class TDLookUpEPHandler. After finding a TD, the code adds a comma (line 62) after every TD.
However, in the case where there are no more TDs matching our query, the comma remains there and it is not deleted creating a malformed JSON.
The code should check in line 78, if there is a comma and remove it before adding the closing bracket ('}'). Right now, the code only omit the comma in case the TD is the last one from the list which is just one specific corner case.

Error in this line:

Thanks,

Oscar

Proposed feature: add all fields from TD

When registering a TD, certain fields are not stored in the thingweb directory. E.g. the created, lastModified and version fields are lost and not visible when retrieving a TD. The same applies to securityDefinitions.

I propose to keep all fields of a TD, even those which are currently unknown to the thingweb directory.

Fields in other (user-defined) namespaces are kept, however a prefix used is expanded using the information from @context. This might be correct, but I would prefer to get the original prefixed version back on retrieval.

Manage TD entries using periodic lifetime refresh

We might point out that using PUT on a registered TD location with an empty payload refreshes the lifetime of the TD on the server, without changing the registered TD.

A good way to manage TD lifetime is to set up your registration client to periodically refresh the lifetime of all currently exposed thing TDs by sending a PUT to each TD location e.g. every 300 seconds.

Then, set the lifetime to something greater, like 600 seconds (?lt=600)

If the server dies or shuts down, the registration will eventually time out.

It's a good idea to track your TDs and delete them when you're shutting down the server also.

pb creating the TemperatureSensorTD using the sample jsonld file

Hi,
we have got an error message when creating (using POST with the payload containing the content of the TemperatureSensorTD.jsonld found in the "samples" directory) the TemperatureSensorTD. Here is the begining of the payload:

{
"@context": [
"http://w3c.github.io/wot/w3c-wot-td-context.jsonld",
{
"saref": "http://uri.etsi.org/m2m/saref#",
"Sensor": "saref:Sensor",
"Temperature": "saref:Temperature",
"unit": "saref:isMeasuredIn",
"celsius": "http://www.wurvoc.org/vocabularies/om-1.8/degree_Celsius"
}
],
"@type": "Sensor",
"name": "myTempSensor5",
"base" : "coap:///www.example.com:5687/temp",
"interaction": [
{

Here is the error message:

<title>Error 500 </title>

HTTP ERROR: 500

Problem accessing /td. Reason:

        <pre>    javax.servlet.ServletException: No instance of td:Thing found in the RDF payload</pre>
    </p>
    <hr />
    <a href="http://eclipse.org/jetty">Powered by Jetty:// 9.3.6.v20151106</a>
    <hr/>
</body>

when replacing the line "@type": "Sensor",
with :
"@type": ["Thing", "Sensor"]
Or
"@type": ["Thing"]
(found in other TD json files)
It works
We also noticed that the description of the thing (using the GET method) is slimmer than the description we provided (the payload of the POST method)

Any idea why?

StackOverflowError in case of name conflict

When a name conflict occur in a TD, the method TDTransform.asJsonLd11ForType() runs into an infinite loop. E.g. (conflictingName used twice):

{
  "id": "tag:something",
  "properties":
    "conflictingName": {
      "type": "object",
      "properties": {
        "conflictingName": {
          "type": "string"
        }
      }
    } 
}

CoAP port 5683 conflicts with same used by iot-rest-api-server

The IoT REST API Server, used by OCF to convert OCF resources from CoAP to HTTP, also wants to bind port 5683 for CoAP services. Trying to start the thing directory on the same computer an iot-rest-api-server is also running causes an error when the thing directory tries to bind the same port. This is non-fatal (the http server still comes up) but is problematic, especially if both the thing directory and the iot-rest-api-server are started automatically (in which case there would be a race condition on who can grab the port first...).

As a workaround, the COAP_PORT property in Californium.properties can be changed to avoid a conflict (I changed mine to 5684).

COAP_PORT=5684

[EDIT: See below, this a poor choice, as it conflicts with COAPS. 15683 is what I am trying to use now.]

Of course this may cause issues with devices looking for CoAP resource directories in a certain place... to discuss.

As a related issue, gateways are often (should be) running firewalls. You may have to explictly open the relevant ports to make the thing directory service available locally to other devices. I used the following, (similar to what is described in the iot-rest-api-server documentation) to open my (re-defined) CoAP port:

sudo iptables -A INPUT -p udp --dport 5684 -j ACCEPT

The default HTTP ports don't conflict since iot-rest-api-server uses 8000 by default (for HTTPS too) and the thing directory uses 8080.

POST application/sparql-query to /td-lookup/sem

Writing URI queries is quite tedious. Thus, it would be better, when also a POST (and CoAP FETCH) would be allowed to the semantic look-up resource with a full SPARQL query in the request body.

Frontend XHR does not handle errors

The Directory Web frontend is very nice. Unfortunately, the XHR object does not have an error handler that would inform about errors such as the (limited..) 500 response when the TD is somehow incorrect.

Since the user cannot know what is going wrong and people tried reloading the frontend and sending again, I classify this as a bug.

Add instructions to start as a service

I want this to start as a service whenever the gateway reboots. To get this to work some specific settings are needed. It would be useful to include a systemd service file in the distribution and some instructions on how to install it. I'm using the following but it may or may not have all the things needed (for example, cleanup of the db on shutdown, restart on crash, etc):

[Unit]
Description=Thing Directory
Requires=network.target
After=network.target

[Service]
#Restart=always
#RestartSec=20
User=thingdirectory
ExecStart=/usr/bin/java -jar /opt/thingweb-directory/build/libs/thingweb-directory-0.7.jar -c 15683 -h 8080 -d /opt/thingweb-directory/db -l /opt/thingweb-directory/Lucene /opt/thingweb-directory

[Install]
WantedBy=multi-user.target

Note I run this with an account with normal user privileges created for the purpose. To install, copy the above to /etc/systemd/system/thing-directory.service and invoke

sudo systemctl enable thing-directory.service
sudo systemctl start thing-directory.service

Also, the following commands are useful for monitoring the service:

sudo systemctl status thing-directory
sudo journalctl -u thing-directory.service

And for shutting it down/turning off automatic startup on boot:

sudo systemctl stop thing-directory.service
sudo systemctl disable thing-directory.service

~

After deleting a TD I cannot upload a new TD with the same id

After deleting a TD using a HTTP DELETE request, the TD does no longer show up in the query interface. However when I try to upload a new TD with the same ID as the deleted one I get a 204 response, which typically occurs when the id already exists.

So uploading a new version of a thing using this approach seems not to be possible.

Registration of a TD gives 500 ERROR - version 10

I created Postman client based on Swagger documentation (api.json file) and tried to register new thing. I got 500 ERROR (Problem accessing /td).

(I set up version 10 according to this guideline #33)

This is the thing that I want to register:

{
  "name":"My Lamp",
  "type": "alien-thing",
  "description": "A web connected lamp",
  "properties": {
    "on": {
      "type": "boolean",
      "description": "Whether the lamp is turned on",
      "href": "/things/lamp/properties/on"
    },
    "brightness" : {
      "type": "number",
      "description": "The level of light from 0-100",
      "minimum" : 0,
      "maximum" : 100,
      "href": "/things/lamp/properties/brightness"
    }
  },
  "actions": {
    "toggle": {
      "description": "Toggle the lamp on and off"
    }
  },
  "events": {
    "overheating": {
      "description": "The lamp has exceeded its safe operating temperature"
    }
  },
  "links": {
    "properties": "/thing/lamp/properties",
    "actions": "/things/lamp/actions",
    "events": "/things/lamp/events"
  }
}

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.