Tip: Developing THETA "Client Mode" Applications

There’s an extensive discussion of the Postman Digest Auth here:

An interesting point is that the Realm and Nonce for Digest Auth needs to be filled in. Right now, I don’t know what this means:


I person I know created a Qt test framework and has it working. I don’t have the code to his Qt test framework, so I’m trying to use Postman for my own test.

I’m not sure what the pollingDelay is:

image

I believe the Digest realm is “RICOH THETA V”
and the nonce is generated on a per session basis.

I’m now getting this in my headers.

I have a working Python script for client mode with Digest Authentication. Here’s the gist.

Here’s the log from the script. I verified the the picture was taken.

I’m now using Python zeroconf for discovery during testing.

With this script

This is what I’m getting back:

Service THETAYL00101082._osc._tcp.local. of type _osc._tcp.local. state changed: 
ServiceStateChange.Added
Address: 192.168.2.101:80
Weight: 0, priority: 0
Server: THETAYL00101082.local.
No properties

curl examples

Curl works on Windows 10 with the THETA in client mode.

GET example for osc/info

$ curl -D - --digest -u "THETAYL00101082:00101082" 'http://192.168.2.101/osc/info'

POST example for osc/state

POST Example
Note the use of -H for the header

$ curl -H "Content-Type:application/json" -D - --digest -u "THETAYL00101082:00101082" -X POST 'http://192.168.2.101/osc/state'

POST Example with data payload to takePicture with osc/execute

$ curl -d '{"name":"camera.takePicture"}' -H "Content-Type:application/json" -D - --digest -u "THETAYL00101082:00101082" -X POST 'http://192.168.2.101/osc/commands/execute'

1 Like

@codetricity we noticed very strange behaviour from Theta V (on 2 devices)
It is randomly hanging. If we are asking every 10 seconds or every few minutes for list of files in some time it stops responding. It is answering to mDNS requests but not TCP or ICMP requests. Sometimes we can call few hundred times sometimes few times until this hang. It is not responding to any device asking. Only shutting down and turning it on again fixes issue until next hang.

Can you confirm that you are having this problem in client mode?

What are you using to test the THETA V API? Is it an Android app on a mobile phone?

Can you provide more information on your test configuration, especially the client command with digest-auth that you’re using to send the request?

Yes, only in client mode. On direct mode it works like charm.
Restlet client, mobile app, python code.
After it hangs it wont respond to osc/info or
/osc/commands/execute

with body:

{
  name: "camera.listFiles",
  parameters: {fileType: "image", entryCount: 120, maxThumbSize: 640}
}

My colleague even made requests from router to check if it will work. So two cameras have same behaviour.
And it doesn’t matter what is making a calls, it will always hang itself

thank you for this detailed response. I will try some tests myself. If I can replicate the failure, I will submit a report to Ricoh. Thanks for the good detail.

Did you try DNS-SD, not mDNS? If you’re on Windows, you can use Bonjour Print Services for Windows to support DNS-SD.

I’ll try and get more info on this, but I think that the camera may not support mDNS right now, only DNS-SD.

Theta is responding to DNS calls while being hung. Which means, we can discover it over network but we can’t call any API because it will timeout. As far as i remember Android NSD uses DNS-SD. Python code used mDNS

I’ve updated camera to latest update (so update was made today). Issue persist. After some random time(and number of requests), camera stops responding to any api calls but it is still visible in network
i’m also checking it via: “avahi-discover” command on my linux.

From my further tests, when camera hangs, i was able to discover via avahi, but while clicking for more details avahi also returns timeout: “Error: org.freedesktop.Avahi.TimeoutError: Timeout reached”. It looks like internal server is shutting down

You have a great point here. I believe the THETA V client mode now works with mDNS as well as DNS-SD.

Testing is difficult right now as there are differences in the network which makes the problems difficult to replicate. I’ll keep trying and will also send this information to a guy I know at Ricoh.

I’ve been thinking about this more. As the THETA V is using Network Service Discovery, I think that DNS-SD is the main supported method.

NSD implements the DNS-based Service Discovery (DNS-SD) mechanism, which allows your app to request services by specifying a type of service and the name of a device instance that provides the desired type of service. DNS-SD is supported both on Android and on other mobile platforms.

While mDNS does work, it is probably not tested as thoroughly. I’m still thinking that we should try and use DNS-SD when possible.

I know a developer that is using this for testing:

https://doc.qt.io/archives/qq/qq23-bonjour.html

Testing dns-sd from Mac OS X

find available THETA V cameras

dns-sd -B _osc._tcp

find IP address

ping Instance_name.local

Example of finding IP address with ping for testing

image

Alternate way to find IP address with dns-sd

 dns-sd -G v4 THETAYLXXXXXXXX.local

Example of finding IP address using dns-sd

image

1 Like

New video provides an introduction to the basic concepts of developing a client mode application.

Hello, I saw this Address written in Python for THETA, sorry I am not familiar with Python, may I ask, how do I implement this with JAVA?

Are you writing a Java (plug-in or Android) application? Or, are you just looking for the IP address?

https://developer.android.com/training/connect-devices-wirelessly/nsd

You can probably find the device if you look for the string below.

    _osc._tcp.

Once you locate the device, use digest authentication when you send the OSC (WebAPI) commands.

For digest auth, I have not tried the solutions below myself, but other people seem to have it working. If you implement something, please post an example.

https://issuetracker.google.com/issues/36919136#comment13

https://www.example-code.com/android/http_authentication.asp

Important If you are developing a plug-in, there is a different method to use the WebAPI. The above assumes you are working on an Android mobile application.

1 Like

Thank you for your reply, haha, I am developing the Android mobile terminal. The client mode of THETA V has been bothering me for a long time, until I saw your post yesterday. That Android Developers page is very helpful to me, thank you very much.

2 Likes

Jay Goldman suggested this on a comment in DZone. I have not tested this yet:

https://www.dotnetcurry.com/nodejs/1237/digest-authentication-nodejs-application

If someone gets node or some type of JavaScript working with Digest Authentication to the THETA in Client Mode, please post a working example.

Thanks.

Update December 11, 2019

Update May 19, 2020

I moved the key points of the discussion to this article.

There are two ways to connect your mobile app to the RICOH THETA with Wi-Fi.

  1. Access Point (AP) mode where the THETA camera functions as a hotspot. The mobile phone connects to the THETA as if the camera were a hotspot or Wi-Fi router

  2. Client Mode (CM) where the THETA camera connects to your home or office router. Your mobile phone connects to the same router

Authentication

The RICOH THETA requires Digest Authentication for client mode. When you use client mode, you must use Digest Authentication in addition to the username and password.

On the THETA V, the username is similar to this: THETAYL00105377

The password is the numerical digits. Example: 00105377

HTTP GET example

In the example below, I am using curl on Linux Ubuntu 20.04 from the command line to test a HTTP GET command to a RICOH THETA V. You can also run curl on Mac or Windows.

$ curl --digest --user "THETAYL00105377:00105377" -X GET http://192.168.2.101/osc/info

Response

{"api":["/osc/info","/osc/state","/osc/checkForUpdates","/osc/commands/execute","/osc/commands/status"],"apiLevel":[2],"_bluetoothMacAddress":"00:26:73:D5:4C:40","endpoints":{"httpPort":80,"httpUpdatesPort":80},"firmwareVersion":"3.21.1","gps":false,"gyro":true,"manufacturer":"RICOH","model":"RICOH THETA V","serialNumber":"00105377","supportUrl":"https://theta360.com/en/support/","uptime":1555858,"_wlanMacAddress":"00:26:73:D5:AA:64"}

HTTP POST example

When you use POST, you must include the header.

curl --digest --user "THETAYL00105377:00105377" -H "Content-Type:application/json" -X POST http://192.168.2.101/osc/state

Response

{"fingerprint":"FIG_0067","state":{"_apiVersion":2,"batteryLevel":1.0,"_batteryState":"charged","_cameraError":[],"_captureStatus":"idle","_capturedPictures":0,"_latestFileUrl":"http://192.168.2.101/files/150100525831424d42079d18e0b6c300/100RICOH/R0010048.JPG","_pluginRunning":false,"_pluginWebServer":false,"_recordableTime":0,"_recordedTime":0,"storageUri":"http://192.168.2.101/files/150100525831424d42079d18e0b6c300/"}}

HTTP POST with data payload

The next example takes a picture.

curl -d '{"name":"camera.takePicture"}' --digest --user "THETAYL00105377:00105377" -H "Content-Type:application/json; charset=utf-8;" -X POST http://192.168.2.101/osc/commands/execute

Response

{"id":"29","name":"camera.takePicture","progress":{"completion":0.00},"state":"inProgress"}