Git Product home page Git Product logo

coapthon's People

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  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  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

coapthon's Issues

Serializer.deserialize restricted to handling of Integers and Strings

using byte values in CoAP options can lead to conversion errors.

E.g. using the ETAG option which is considered to contain an OPAQUE content, is forced to be converted to a string which ends up in

UnicodeDecodeError: 'ascii' codec can't decode byte 0xff in position 0: ordinal not in range(128)

Resource max-age implementation

Does max-age is been used somehow, except as data field in resource? It seems, that it affects nothing when running coapreverseproxy.py example. Should max-age field be processed in self-written proxy server?

Creating a resource tree leaving out intermediate nodes

Hi,

I have a question regarding "add_resource" from server\coap.py: Why don't we allow to leave out intermediate nodes while creating a resource tree? For example:

/small
/large
/other/color
/other/transparence

Why do we have to define /other before creating the sub nodes?

Regards

coapclient.py arguments

pi@raspberrypi:~/CoAPthon $ python coapclient.py
Operation must be specified
Command: coapclient.py -o -p [-P]
Options:
-o, --operation= GET|PUT|POST|DELETE|DISCOVER|OBSERVE
-p, --path= Path of the request
-P, --payload= Payload of the request
-f, --payload-file= File with payload of the request

if anyone can help in better understanding what the arguments mean and how the client and server transfer data it will be much appreciated.

Thanking in anticipation.

regards
@rajshah

Add and Edit resource fails on POST

File layer\resource.py lines 80 and 183 raise TypeError. This is because the self._parent is of type coapthon2.server.coap_protocol.CoAP and origin_class is a subclass of Resource.

Not clear the intention of that part of code. Do you mean self._parent.root.value?

How do I make a resource observable and send notifications?

I'm trying to configure a Resource to act as observable. "Observable" is set to true but how do I define/implement when to send the notifications? (I haven't found an example nor test that do this).

All resources inherite from coapthon2.resource.resource which has the _observable and _observe_count member variables. CoAP() has the functionality of notify() and prepare_notification() which seems useful but I don't really understand how all parts fit together at the moment and I might have too many moving targets trying to debug the server with Copper firefox plugin (sending observe messages that even wireshark can't dissect).

My best bet is to use prepare_notification() somehow but not sure how to properly create a thread (or use existing one) so I don't lock processing of incoming requests (looping in my render_GET() seems wrong).

My questions

  1. Is Resource.Resource._observe_count the counter for number of clients that are observing that specific resource (default value of 1 doesn't make sense if that is the case)?
  2. Generating the documentation for "layer.observe" gives some odd explanation. The "parameters" explanation for "notify" is the same as for "notify_deletion".
  3. How do I define/implement when to send notifications?

Socket leaks when HelperClient is stopped.

When I repeatedly create HelperClients within the same process, i.e.,

while True:
    c = HelperClient(...)
    c.get(...)
    c.stop()
    sleep(...)

I would expect at most one socket to be open. On Linux if I watch what happens using netstat, I see that the process rapidly accumulates sockets, one for every new HelperClient, even though each client is stopped.

This seems to be down to only doing socket.close() on stop inside the client - if I manually try call socket.shutdown(socket.SHUT_RDWR) before stop the socket appears to be cleaned up correctly.
This seems to be a Python socket 'feature', even for UDP: https://engineering.imvu.com/2014/03/06/charming-python-how-to-actually-close-a-socket-by-calling-shutdown-before-calling-close/

On 4.0.2 I can work around this by manually supplying a socket and shutting it down myself, but the built-in socket should really do this too.

Integer CoAP options are not handled correctly

Trying to deserialize a CoAP message with content-type option like so:

from coapthon.messages.request import Request
from coapthon.messages.option import Option
from coapthon import defines
from coapthon.serializer import Serializer

r = Request()
r.mid = 0
r.code = defines.inv_codes["GET"]
r.type = defines.inv_types["CON"]
opt = Option()
opt.number = defines.inv_options["Content-Type"]
opt.value = defines.inv_content_types["text/plain"]
r.add_option(opt)

ser = Serializer()
bytes = ser.serialize(r)
msg = ser.deserialize(bytes, None, None)

Results in TypeError:
Traceback (most recent call last): File "test.py", line 17, in <module> msg = ser.deserialize(bytes, None, None) File "/home/jaakuk03/Development/CoAPthon/coapthon/serializer.py", line 99, in deserialize value = (value << 8) | b TypeError: unsupported operand type(s) for |: 'int' and 'str'

How to handle runtime errors

errors

def connect_server(self, message):
try:
print "\n + Preparing to connect."
client = HelperClient(message.destination)

        print "\n + Observing start."
        if message is not None:
            print "\n + Connection established."
            received_message = client.send_request(message)
            print received_message
            if received_message:
                print "\n + Validating response."
                print received_message.mid
                print received_message.token
                print received_message.payload
            client.stop()
            print "\n + Connection Closed."
    except:
        print "Errors"
    finally:
        # Finally clause:
        print("Finally clause reached")

but not handling in errors

i am trying to handle server unavailability event .

IPv6 support

Am I able to use IPv6 addresses in reverse-proxy xml mapping?

Support for RESTful resource URI

I am trying to implement a CoAP server that handles requests of the following format:

GET /element to select all elements
GET /element/:id e.g. /element/12 to select a specific element
GET /element/:id/property to get a certain property of a specific element

Is there any way to do this with this library? I could not directly find support for such a thing.

Implement DTLS support

I'm interested in using a Python CoAP client library for a project that requires security. I happened upon this library and was pleased to see recent activity. Is there a likely timeframe for implementing DTLS support?

Blockwise support

Would you be able to implement blockwise transfers in near future ?
From all python 2.x CoAP implementations, this one seems to be the best, but I would really appreciate blockwise support.

Thanks!

CoAPthons empty ACK echo token

When sending a GET request to URI path "/seperate" of the coapserver.py example using a CON message with a token, the empty ACK echos the token of the CON message. Correct would be to only echo the message ID and not sending a token.

In the CoAP specification Section 2.2 in figure 4 piggybacked responses are shown, where the ACK does contain a token (as it contains a response to match a request). In figure 5 a separate response is shown and the ACK does not contain a token, but the delayed response does.

Regards,
maribu

Need help in setting up coap server

Hello,
I am trying to use CoAPthon to open a server and client with port 5683 simultaneously. The idea is CoAPthon server to receive any instantaneous request from external coap client. CoAPthon client is sending ping request to external soap server. All coap transactions are on port 5683. CoAPthon client is able to ping external coap server, but external coap client is not able request CoAPthon server.
When I start the server by running cia-server.py script, I see the server started with device ip address and port 5683. But when I am sending request from external server I don't see any message received by CoAPthon server.
Is there something I am missing. Any help is appreciated

Thanks,
Prasant

Starting server with a Multicast IP

Hello, I'm trying to start the Server with a Multicast IP:

python coapserver.py -i 224.0.1.187 -p 5683

The result is the following error message:

socket.error: [Errno 10049] The requested address is not valid in its context

Token of OBSERVE in client is always overwritten with 'ciao'

Line 331 in client/coap_protocol.py the 'Token' is always overwritten with 'ciao'. Is that intentional?

Function: def observe(self, client_callback, _args, *_kwargs):
Line 320 retrieves the 'Token' from the arguments but in line 331 the 'Token' is overwritten with a default 'ciao'.

incorrect handling of dublicate messages

Hi kind sir,

Thank you for implementing this for Python, saved much time and headache.
I've noticed that if the default server listener is used, then the dublicate message is handled incorrectly - server sends response and returns from listen() and thus is stopped. I think there should be continue instead of return.

Server auto-token generation breaks RFC 7252

From RFC 7252, section 3.5.2:

In a piggybacked response, the Message ID of the Confirmable request and the Acknowledgement MUST match, and the tokens of the response and original request MUST match. In a separate response, just the tokens of the response and original request MUST match.

When sending an empty token to a CoAPthon server (something that the RFC specifies to be doable and that CoAPthon clients do) the CoAPthon server generates a token and sends it back to the client. Lets call this behaviour CoAPthon server's auto-token generation.

Most clients, incliuding CoAPthon, don't check the returning token when they sent it empty so this CoAPthon server's auto-token generation behaviour does not influence them, but to fulfill the RFC 7252 the clients should reject ACKs with a token not corresponding to the one they sent, as specified a couple lines below the previous cite:

In case a message carrying a response is unexpected (the client is not waiting for a response from the identified endpoint, at the endpoint addressed, and/or with the given token), the response is rejected (Sections 4.2 and 4.3).

Thus, CoAPthon server's auto-token generation breaks the RFC and should be avoided (if the token is used internally, at least it shouldn't be sent in the ACK message if the CON request had an empty token.

Additionally, to fulfill the RFC fully, CoAPthon client should check that the ACK token matches. This second part is not broadly extended among client implementations (and you could always interpret this behaviour not to be mandatory as sending an empty token implies you are not expecting anything, thus not receiving an unexpected token), so implementing should be lower priority, but server auto-token generation must be removed to fulfill RFC 7252.

Coap DTLS Client and Server

Hi,

I am planning to use Coap DTLS client from this library "test_secure.py". But i am using javascript webserver as my Coap Server. So, my question- will following piece of code will work to validate the key that has been used from the test_secure,py ?

const coap = require('../') // or coap
const path = require('path');

var SegfaultHandler = require('segfault-handler');

SegfaultHandler.registerHandler("crash.log"); // With no argument, SegfaultHandler will generate a generic log file name

const dtls_opts = {
key: path.join(__dirname, '/test/server.pem'),
debug: 1,
handshakeTimeoutMin: 3000
};

const server = coap.createServer(
{
dtls: dtls_opts,
port: 5684,
}
);

server.on('request', function(req, res) {
console.log('request arrives:\n'+JSON.stringify(req));
res.end('Hello ' + req.url.split('/')[1] + '\n')
})

server.listen(function() {
console.log('server started')
});

Thanks,
Jyoti Raj

Observe seems not to work for local changes

I am implementing an IoT_Lab for Students. The aim is to develop a coapserver which serves different actors and sensors connected to a pi as resources.

My proof of concept fails at quite a simple Task. I Have a Button which polls its Value periodically and if it sees a change, writes the changed property. But it seems the changedproperty is not read by the server, so no notification to the observers is sent.
I can no see any other way to notify the server about a changed sensor value, is observ only implemented for changes which result through a coap request?

IPv6 support: token error on response when the address is not compacted

Hello,

I'm opening this issue in link with #37 .
I commented over there, but it went unnoticed, and it's an unrelated problem.

I'll write down below what I posted over here.

I'm sorry for reopening this issue, but there is still a little bug.

It's when you do a request with a full IPv6 (example fd01:0000:0000:3ead:c5b2:bad0:6bb1:6dbf) but when the response received only gives back the shortened address (aka fd01::3ead:c5b2:bad0:6bb1:6dbf).

I believe the trouble starts here (or end here ;-) ), line 108 in messagelayer.py, function receive_response. This function hashes the tuple (host, port, response.mid), with the data received in the response, and then tries to compare it with the hash made in the function send_request, in the same file at line 216.

So I believe the function parse_uri (here) could be modified to include a contraction of the consecutive 0 in IPv6 addresses.

Server non può fare il join in gruppi differenti (defines.ALL_COAP_NODES)

Ciao Giacomo,

siamo due tesisti che studiano il CoAP(ti avevamo già contattato in precedenza via email) e stiamo utilizzando la tua implementazione. Per il nostro progetto abbiamo modificato il file coapthon/server/coap_protocol.py in quanto non rendeva possibile al server il join a gruppi differenti da quello da te definito in defines.ALL_COAP_NODES. Abbiamo risolto implementando una funzione che permettesse di scegliere il gruppo appena istanziato e cambiando di conseguenza il parametro in ingresso alla funzione di join:

Funzione definita :

def setGroup(self,g):
self.group = g

Riga 79 del medesimo file

self.transport.joinGroup(self.group)

Facci sapere cosa ne pensi, o se quanto da te fatto era una semplice scelta progettuale.

Separate responses not working

For a separate response to work there needs to be a token. The HelperClient only has a token for the Post method (not that it works because other code needs it to be lower case).

I have attached a patch with changes to helperclient.py with the tokens added. The patch has also got changes to allow a timeout to be set through the helper methods.
CoAPthonHelper.zip

PUT response with payload

First, thank you for this library.

I'm trying to get a PUT response with a payload, however I'm not able to do it, the response always comes with an empty payload. Is it possible to do so with this library?

Here is the relevant part of my code:

def render_PUT(self, request):
    if request.payload == "0":
        self.payload = "message 1"
    else:
        self.payload = "message 2"
   return self

reactor.listenUDP in coapserver.py fails

Traceback (most recent call last):
File "coapserver.py", line 24, in
main()
File "coapserver.py", line 19, in main
reactor.listenUDP(5683, server, "127.0.0.1")
File "C:\Program Files (x86)\Python\lib\site-packages\twisted\internet\posixbase.py", line 364, in listenUDP
p.startListening()
File "C:\Program Files (x86)\Python\lib\site-packages\twisted\internet\udp.py", line 102, in startListening
self._connectToProtocol()
File "C:\Program Files (x86)\Python\lib\site-packages\twisted\internet\udp.py", line 123, in _connectToProtocol
self.protocol.makeConnection(self)
File "C:\Program Files (x86)\Python\lib\site-packages\twisted\internet\protocol.py", line 691, in makeConnection
self.doStart()
File "C:\Program Files (x86)\Python\lib\site-packages\twisted\internet\protocol.py", line 655, in doStart
self.startProtocol()
File "D:\[email protected]\projects\EIT ICT\RICH\CoAPthon\coapthon2\server\coap_protocol.py", line 67, in startProtocol
self.transport.joinGroup(defines.ALL_COAP_NODES)
AttributeError: 'Port' object has no attribute 'joinGroup'

"Get" and "Put" example

Is there any way to pull out "Get" and "Put" module ?

I want to control Led through "PUT" and acquire fixed sources data through "GET".

No license

There is no license in the repository.

What Python version is required?

I'm trying to find out which Python version this is targetted at. The 'print' statements suggest it's Python 2.x, but when I try running it (e.g. coapserver.py) it can't import 'concurrent.futures', which is a Python 3.x module. How can I get this to run?

Thanks
Ian

message id does not wrap

The code at the moment does not wrap the message id when it reaches 65525. The += 1 needs to be on a separate line so that it happens before the modulo.

patch.zip

blocklayer bug and possible mishandling of duplicates

With intermittent connections, where duplicate requests end up being generated, the following happens:
(client)

self._blockLayer.receive_response(transaction)
File "/usr/local/lib/python2.7/dist-packages/coapthon/layers/blocklayer.py", line 182, in receive_response
transaction.response.payload = self._block2_sent[key_token].payload + transaction.response.payload
TypeError: cannot concatenate 'str' and 'NoneType' objects

This occurred using the forward proxy (with multiple simultaneous requests) and the problem seems to be, after correctly receiving the first block, the sending of a delayed response/ACK to the initial request but as if it was block 2 with 0 bytes:

(forward proxy)

2017-04-10 11:34:19,463 - MainThread - coapthon.forward_proxy.coap - DEBUG - receive_datagram - From ('a:1::10', 47197), To None, CON-21046, GET-None, [Uri-Path: big, Proxy-Uri: coap://[a:2::20]:5683/big/, ] No payload
2017-04-10 11:34:19,463 - MainThread - coapthon.layers.messagelayer - DEBUG - receive_request - From ('a:1::10', 47197), To None, CON-21046, GET-None, [Uri-Path: big, Proxy-Uri: coap://[a:2::20]:5683/big/, ] No payload
2017-04-10 11:34:19,464 - MainThread - coapthon.forward_proxy.coap - DEBUG - message duplicated,transaction completed
2017-04-10 11:34:19,464 - MainThread - coapthon.layers.messagelayer - DEBUG - send_response - From None, To ('a:1::10', 47197), ACK-21046, CONTENT-None, [Block2: 22, ] ...0 bytes
2017-04-10 11:34:19,473 - MainThread - coapthon.forward_proxy.coap - DEBUG - send_datagram - From None, To ('a:1::10', 47197), ACK-21046, CONTENT-None, [Block2: 22, ] ...0 bytes

More complete output from the client side:

2017-04-10 11:34:01,852 - MainThread - coapthon.layers.messagelayer - DEBUG - send_request - From None, To ('a:1::1', 5683), CON-21046, GET-None, [Uri-Path: big, Proxy-Uri: coap://[a:2::20]:5683/big/, ] No payload
2017-04-10 11:34:01,855 - MainThread - coapthon.client.coap - DEBUG - send_datagram - From None, To ('a:1::1', 5683), CON-21046, GET-None, [Uri-Path: big, Proxy-Uri: coap://[a:2::20]:5683/big/, ] No payload
2017-04-10 11:34:01,856 - Thread-1 - coapthon.client.coap - DEBUG - Start receiver Thread
2017-04-10 11:34:01,857 - MainThread-Retry-21046 - coapthon.client.coap - DEBUG - retransmit loop ... enter
2017-04-10 11:34:04,451 - MainThread-Retry-21046 - coapthon.client.coap - DEBUG - retransmit loop ... retransmit Request
2017-04-10 11:34:04,459 - MainThread-Retry-21046 - coapthon.client.coap - DEBUG - send_datagram - From None, To ('a:1::1', 5683), CON-21046, GET-None, [Uri-Path: big, Proxy-Uri: coap://[a:2::20]:5683/big/, ] No payload
2017-04-10 11:34:09,647 - MainThread-Retry-21046 - coapthon.client.coap - DEBUG - retransmit loop ... retransmit Request
2017-04-10 11:34:09,653 - MainThread-Retry-21046 - coapthon.client.coap - DEBUG - send_datagram - From None, To ('a:1::1', 5683), CON-21046, GET-None, [Uri-Path: big, Proxy-Uri: coap://[a:2::20]:5683/big/, ] No payload
2017-04-10 11:34:19,461 - Thread-1 - coapthon.client.coap - DEBUG - receive_datagram - From ('a:1::1', 5683), To None, ACK-21046, CONTENT-None, [Block2: 14, ] Lorem ipsum dolor si...1024 bytes
2017-04-10 11:34:19,461 - Thread-1 - coapthon.layers.messagelayer - DEBUG - receive_response - From ('a:1::1', 5683), To None, ACK-21046, CONTENT-None, [Block2: 14, ] Lorem ipsum dolor si...1024 bytes
2017-04-10 11:34:19,461 - Thread-1 - coapthon.client.coap - DEBUG - Waiting for retransmit thread to finish ...
2017-04-10 11:34:19,471 - Thread-1 - coapthon.client.coap - DEBUG - Waiting for retransmit thread to finish ...
2017-04-10 11:34:19,482 - Thread-1 - coapthon.client.coap - DEBUG - Waiting for retransmit thread to finish ...
2017-04-10 11:34:19,490 - MainThread-Retry-21046 - coapthon.client.coap - DEBUG - retransmit loop ... exit
2017-04-10 11:34:19,492 - Thread-1 - coapthon.layers.messagelayer - DEBUG - send_request - From None, To ('a:1::1', 5683), CON-None, GET-None, [Uri-Path: big, Proxy-Uri: coap://[a:2::20]:5683/big/, Block2: 22, ] No payload
2017-04-10 11:34:19,498 - Thread-1 - coapthon.client.coap - DEBUG - send_datagram - From None, To ('a:1::1', 5683), CON-6285, GET-None, [Uri-Path: big, Proxy-Uri: coap://[a:2::20]:5683/big/, Block2: 22, ] No payload
2017-04-10 11:34:19,499 - Thread-1-Retry-6285 - coapthon.client.coap - DEBUG - retransmit loop ... enter
2017-04-10 11:34:19,500 - Thread-1 - coapthon.client.coap - DEBUG - receive_datagram - From ('a:1::1', 5683), To None, ACK-21046, CONTENT-None, [Block2: 22, ] No payload
2017-04-10 11:34:19,500 - Thread-1 - coapthon.layers.messagelayer - DEBUG - receive_response - From ('a:1::1', 5683), To None, ACK-21046, CONTENT-None, [Block2: 22, ] No payload
Exception in thread Thread-1:
...

Generating documentation gives bitstring errors

I followed the install instructions in the README and it all seemed to work but the bitstring package didn't install properly. I noticed this when generating documentation. Bitstring is mentioned in the requirements.txt file so it should have worked the first time around.

I just ran "sudo pip install bitstring" and it installed fine and now I can generate documentation properly. I will see if I get time to reproduce the installation error later on in a VM.

Unable to get response from CoAP server

Hello, I have implemented the server as mention in read_me file. When i issue the start command via putty it gives be response as below:
coapserver
Now when i try to access this via Firefox plugin "Copper" it gives me no response.

Can you please help me? What i actually want to do is to run a server with CoAP, so that all my iot devices can communicate via coap. Any help will be appreciated.

Coapforwardproxy

how to use coapforwardproxy between coapclient and coapserver

The re-transmission mechanism stops in case of block-wise POST for a lossy link

We have investigated the problem. It seems that once one block is successfully transferred the message.acknowledged flag is set to true. However, as soon as a next block hits hits the timeout it does not enter the re-transmission logic.
Probably because the line #125 in client/coap.py:
`while retransmit_count < defines.MAX_RETRANSMIT and (not message.acknowledged and not message.rejected) \

  •                and not self.stopped.isSet():`
    

the "message.acknowledged" is True due to the prior success of the earlier block. So, the loop is not actually entered and the client keeps waiting checking whether file descriptor was set rather then proactively setting the descriptor through re-sending the datagram.

how to use observe in CoAPthon ?

I was trying to carry out function of observe by changing value of payload to present time of ObservableResource in Plugtest_resorces.py. but it always reponse blank payload(i tried to access from fitefox to coap)

Unable to send Observe notifications to client

Dear Sir

I have created an RandomResource in exampleresources.py and would like to send an random value to the client for every 5 seconds using an thread RandomThread , I used RandomResource._coap_server.notify(RandomResource) to send the updated value. Please take a look through the code. Don't know what mistake am doing

class RandomResource(Resource):

class RandomThread(threading.Thread):
    def run(self):
        while True:
            sleep(5)
            randnum = randint(1,50)
            RandomResource.payload="response:" +str(randnum)
            RandomResource._coap_server.notify(RandomResource)

def __init__(self,name="RandomResource",coap_server=None):
    super(RandomResource,self).__init__(name, coap_server, visible=True,
                                       observable=True, allow_children=True)
    try:
        t1 = self.RandomThread()
        t1.start()
    except:
        print "Error: Unable to start thread"

def render_GET(self,request):
    return self

CoAP DTLS example code required

Hi,

I have sent payload message from Raspberry Pi3 via python shell script. However, i need some example code to execute DTLS. Please help to provide example script to run DTLS.

Thanks,
Jyoti Raj Sharma

Pipe leaks from HelperClient due to Python multiprocessing Queue bug

Possibly due to https://bugs.python.org/issue27151, I find that the HelperClient queue is leaking pipes if I create and stop multiple HelperClients in succession.

Regardless of what happens with the multiprocessing queue issue in Python itself, there is no reason HelperClient needs to use a multiprocessing queue at all because it does not do multiprocessing - creating OS pipes is therefore wasteful. To synchronize under multi-threading, the standard synchronized queue class is sufficient.

does CoAP to HTTP proxy is up?

I read on the documentation saying that CoAP to HTTP proxy is in the to do list. Is the development is still in progress?

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.