Eclipse Californium CoAP 通配符作为 url 路径

2024-03-29

我正在使用 Eclipse Californium 开发一个 CoAP 应用程序,它将仅显式声明根资源路径,其余资源应通过通配符提供和解析/root/*就像在 REST API 或 servlet 上一样。

有什么办法可以实现这一点吗?


好吧,我成功了。

因此,经过几个小时的挖掘他们的源代码之后,这就是最终的结果。

请注意,它可以工作,但只是为了展示如何完成它,它仍然是一项正在进行的工作(我在 3 小时内完成了此操作),因为我删除了一些代码,例如观察者等。

一旦我有时间,我将深入研究 Californium Api 并使其通用和优化,我将创建一个 Github 项目并将其链接到此处。

1:创建模型类

public class ProxyRes {

    public  CoapResource coapRes;
    public  String  path;

    public ProxyRes () {
    }

    public CoapResource getCoapRes () {
        return coapRes;
    }

    public void setCoapRes (CoapResource coapRes) {
        this.coapRes = coapRes;
    }

    public String getPath () {
        return path;
    }

    public void setPath (String path) {
        this.path = path;
    }
}

2:创建一个应该注入通配符列表的抽象 CoapResource

public abstract class AbstractResource extends CoapResource {

    private LinkedList<String> wildcards;

    protected AbstractResource (String name) {
        super (name);
    }

    protected AbstractResource (String name, boolean visible) {
        super (name, visible);
    }

    public LinkedList<String> getWildcards () {
        return wildcards;
    }

    public void setWildcards (LinkedList<String> wildcards) {
        this.wildcards = wildcards;
    }
}

3:创建一个扩展 AbstractResource 的温度资源

public class TemperatureResource extends AbstractResource {

    public TemperatureResource () {
        super (ResourceSpecs.House.Sensors.Temperature);

        getAttributes ().setTitle ("Temperature resource !");
    }

    @Override
    public void handleGET (CoapExchange exchange) {
        String response = "The temperature";
        if (getWildcard () != null) {
            response += " of the " + getWildcard ().get (0) + " on the " + getWildcard ().get (1);
        }
        response += " is : 25 degree C";

        exchange.respond (response);
    }
}

4 : 在我的 eclipse 项目的根目录下创建一个 resources 目录,其中包含我的资源的 json conf 文件

{
    "verb": "get",
    "endpoint": "/houses/*/rooms/*/sensors/temperature",

    "class": "com.wild.coap.resources.TemperatureResource"
}

5:创建一个资源加载器(将加载资源的规格定义并独立实例化它们的类,而不是在服务器上创建树)

public class ResourcesLoader {

    private final static String Path = new File (".").getAbsolutePath () + File.separator + "resources";

    private List<ProxyRes>  resourcesList;

    public ResourcesLoader () throws Exception {
        resourcesList   = new ArrayList<ProxyRes> ();

        File resources  = new File (Path);
        for (String resName : resources.list ()) {
            File resFile    = new File (resources, resName);
            InputStream is  = new FileInputStream (resFile);
            JsonObject o    = new JsonObject (is);

            resourcesArr.add (o);
            resourcesList.add (buildObject (o));
        }
    }

    private ProxyRes buildObject (JsonObject o) throws ClassNotFoundException, InstantiationException, IllegalAccessException {
        ProxyRes r = new ProxyRes ();
        r.setPath (o.getString ("endpoint"));

        Class<?> clazz  = Class.forName (o.getString ("class"));
        CoapResource coapRes = (CoapResource)clazz.newInstance ();
        r.setCoapRes (coapRes);

        return r;
    }

    public List<ProxyRes> getResourcesList () {
        return resourcesList;
    }
}

6:创建自定义MessageDeliverer

public class DynamicMessageDeliverer implements MessageDeliverer {

    private final List<ProxyRes>    resources;

    public DynamicMessageDeliverer (List<ProxyRes> resources) {
        this.resources  = resources;
    }

    public void deliverRequest (final Exchange exchange) {
        Request request         = exchange.getRequest ();
        List<String> path       = request.getOptions ().getUriPath ();

        final Resource resource = registerResources (path);     
        if (resource != null) {
            executeResource (exchange, resource);           
        } else {
            exchange.sendResponse (new Response (ResponseCode.NOT_FOUND));
            throw new RuntimeException ("Did not find resource " + path.toString() + " requested by " + request.getSource()+":"+request.getSourcePort());
        }
    }

    private void executeResource (final Exchange exchange, final Resource resource) {
        // Get the executor and let it process the request
        Executor executor = resource.getExecutor ();
        if (executor != null) {
            exchange.setCustomExecutor ();
            executor.execute (new Runnable () {

                public void run () {
                    resource.handleRequest (exchange);
                } 
            });
        } else {
            resource.handleRequest (exchange);
        }
    }

    private Resource registerResources (List<String> list) {
        LinkedList<String> path         = new LinkedList<String> (list);
        String flatRequestedEndpoint    = Arrays.toString (path.toArray ());
        LinkedList<String> wildcards    = new LinkedList <String> ();
        ProxyRes retainedResource       = null;

        for (ProxyRes proxyRes : resources) {
            String[] res = proxyRes.getPath ().replaceFirst ("/", "").split ("/");

            int length = res.length;
            if (length != path.size ()) {
                continue;
            }

            String flatResEndpoint = Arrays.toString (res);
            if (flatResEndpoint.equals (flatRequestedEndpoint)) {
                retainedResource = proxyRes;
                break;
            }

            boolean match = true;

            for (int i = 0; i < length; i ++) {
                String str = res[i];
                if (str.equals ("*")) {
                    wildcards.add (path.get (i));
                    continue;
                }

                if (!str.equals (path.get (i))) {
                    match = false;
                    break;
                }
            }

            if (!match) {
                wildcards.clear ();
                continue;
            }

            retainedResource = proxyRes;
            break;
        }

        if (retainedResource == null) {
            return null;
        }

        ((AbstractResource)retainedResource.getCoapRes ()).setWildcard (wildcards);
        return retainedResource.getCoapRes ();
    }

    public void deliverResponse (Exchange exchange, Response response) {
        if (response == null) throw new NullPointerException();
        if (exchange == null) throw new NullPointerException();
        if (exchange.getRequest() == null) throw new NullPointerException();
        exchange.getRequest().setResponse(response);
        Request request         = exchange.getRequest ();
        List<String> path       = request.getOptions ().getUriPath ();
        System.out.println ("Path retrieved : " + Arrays.toString (path.toArray ()));
    }
}

7:创建服务器

public class WildCoapServer extends CoapServer {

    private static final int COAP_PORT = NetworkConfig.getStandard  ().getInt  (NetworkConfig.Keys.COAP_PORT);

    public WildCoapServer () throws Exception {

        // add endpoints on all IP addresses
        addEndpoints ();

        ResourcesLoader resLoader   = new ResourcesLoader ();
        List<ProxyRes> resources    = resLoader.getResourcesList ();

        setMessageDeliverer (new DynamicMessageDeliverer (resources));
    }

    @Override
    protected Resource createRoot () {
        return new WildRootResource ();
    }

    // Add individual endpoints listening on default CoAP port on all IPv4 addresses of all network interfaces.
    private void addEndpoints () {
        for (InetAddress addr : EndpointManager.getEndpointManager ().getNetworkInterfaces ()) {
            // only binds to IPv4 addresses and localhost
            if (addr instanceof Inet4Address || addr.isLoopbackAddress ()) {
                InetSocketAddress bindToAddress = new InetSocketAddress (addr, COAP_PORT);
                addEndpoint (new CoapEndpoint (bindToAddress));
            }
        }
    }
}

8:启动服务器

public class Main {

    public static void main (String[] args) {

        try {
            WildCoapServer server = new WildCoapServer ();
            server.start ();
        } catch  (Exception e) {
            throw new RuntimeException (e.getMessage (), e);
        }
    }
}

9:从客户端消耗温度资源

public class Client {

    public static void main  (String[] args) {

        URI uri = null;
        try {
            uri = new URI ("coap://192.168.200.1:5683/houses/house1/rooms/kitchen/sensors/temperature");
        } catch  (URISyntaxException e) {
            throw new RuntimeException (e.getMessage (), e);
        }

        CoapClient client       = new CoapClient (uri);

        CoapResponse response   = client.get ();

        if (response != null) {

            System.out.println (response.getCode ());
            System.out.println (response.getOptions ());
            System.out.println (response.getResponseText ());

            System.out.println ("\nADVANCED\n");
            // access advanced API with access to more details through .advanced ()
            System.out.println (Utils.prettyPrint (response));

        } else {
            System.out.println ("No response received.");
        }       
    }
}

希望对某人有帮助。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Eclipse Californium CoAP 通配符作为 url 路径 的相关文章

  • 如何反编译混淆的java程序以避免类/包名称冲突

    我想反编译一个java程序并重新编译派生的 混淆的 源代码 我解压了 jar 存档并得到了如下目录结构 com com foo A com foo A A class com foo A B Class com foo B A class
  • Ant 复制文件而不覆盖

    Is there any command in ant to copy files from one folder structure to another without checking the last modified date t
  • 如何用Spring进行只读和读写的数据库路由

    我正在研究 Spring 中的事务路由 但我的应用程序存在运行时问题 我有两个 MySQL 数据库 一个用于读取 一个用于读 写 但是我的路由配置不起作用 当我应用只读配置时 我没有成功 这是我的配置 pom xml
  • 如何在 El Capitan (OS X 10.11) 中设置 Android Studio?

    全新安装 El Capitan 10 11 尝试安装 Android Studio 版本 1 21 Error Android Studio was unable to find a valid JVM Please download it
  • 如何缓解 Apache Log4j 反序列化 RCE (CVE-2019-17571)

    我已将 log4j core 依赖项升级到 2 15 0 以防止任何潜在的 Log4Shell 攻击 话虽如此 我无法从 1 2 17 升级 slf4j log4j12 的间接 log4j 依赖项 因为 slf4j log4j12 的最新稳
  • java SWT透明复合背景

    我有复合对象 Composite composite new Composite shell SWT NONE composite setBounds new Rectangle 10 10 100 100 我如何使这个组合具有透明背景 我
  • java中的new关键字是多余的吗?

    我来自 C 所以 java 的一个特性我不太理解 我读过所有对象都必须使用关键字创建new 但基元除外 现在 如果编译器可以识别原始类型 并且不允许您在不调用其构造函数的情况下创建对象new 有这个关键字的原因是什么new根本吗 有人可以提
  • GSON 预期为 BEGIN_ARRAY,但实际为 BEGIN_OBJECT

    当我仅收到列表中的一项时 我收到此错误 我在服务器端 REST Web 服务中使用 Jersey 只有当列表返回一个元素并且它具有0 elements I get java lang NullPointerException但是当它有多个时
  • 在 ant 脚本中包含外部 JAR 时出错

    这是我第一次尝试编写 ANT 脚本 这是我使用 Spring 构建的简单 Hello World 应用程序的 build xml
  • 用 org.Json 解析 Java 中的 JSON?

    我在这方面遇到了很多麻烦 我正在尝试进行更新 并且正在使用从 url 返回此内容的 api JSON downloadUrl URL fileName Name gameVersion Version name Name projectId
  • 如何获取eclipse中的工作空间路径? [关闭]

    Closed 这个问题需要细节或清晰度 help closed questions 目前不接受答案 我正在研究PDE Eclipse Plugin Project 我需要获取工作区路径 我的文本小部件 swt 应该设置为当前工作空间路径 如
  • 在可序列化 Java 类中使用记录器的正确方法是什么?

    我有以下 doctored 我正在开发的系统中的类以及Findbugs http findbugs sourceforge net 正在生成一个SE BAD FIELD http findbugs sourceforge net bugDe
  • Spring-WS WSDL生成问题

    我正在尝试制作一个非常简单的 Web 服务 但在让 spring 生成正确的 wsdl 时遇到一些困难 我已尽力复制此示例春季教程 http static springsource org spring ws sites 2 0 refer
  • 在 Spring 中以编程方式解析 AliasFor 注释值

    我有一个注释 Target ElementType TYPE Retention RetentionPolicy RUNTIME public interface A Class value 这是在课堂上使用的 B D class publ
  • Android 中的 RoboSpice 库是什么

    我正在尝试了解 android 中的 RoboSpice 库 我在这里看到了在线文档 https github com stephanenicolas robospice wiki Starter Guide 我尝试过什么 我之前研究过使用
  • 在 Maven Shade 插件中包含依赖项

    我正在尝试使用 Apache 的 commons lang3 创建一个可部署的 jar 但是 我的 Hadoop 所在的 AWS 集群不包含此库 因此我收到了 classNotFoundException 我想我需要手动添加该依赖项 但我在
  • 当考虑性能时如何从文件中读取整数?

    我正在 CodeEval 上执行一些任务 基本上任务非常简单 打印出从文件中读取的所有整数的总和 我的解决方案如下 import java io File import java io IOException import java io
  • Java 压缩字符串

    我需要创建一个接收字符串并返回字符串的方法 防爆输入 AAABBBCCC 防爆输出 3A4B2C 好吧 这很尴尬 我在今天的面试中无法做到这一点 我正在申请初级职位 现在 我在家尝试制作一些静态工作的东西 我的意思是 不使用循环有点无用 但
  • Java邮件,设置回复地址不起作用

    我用java写了一个小的电子邮件发送程序 它有from to and reply to地址 当客户端尝试回复邮件时 应该能够回复reply to地址 目前它不起作用 我的代码如下 File Name SendEmail java impor
  • 如何将钱兑换成零钱

    尝试将输入的数字转换为 25 美分 50 美分 10 美分和 10 分 有几个问题 public class Coins public static void main String args private int quarters di

随机推荐

  • 使用 iTextSharp 提取路径和形状

    iTextSharp 支持创建形状和路径PdfContentByte类 您可以在那里设置颜色并绘制曲线和基本元素 是否有一种机制可以以其他方式执行 我可以通过致电获取内容PdfReader GetPageContent 但我没有找到一个 解
  • 如何将数据帧行分组到pandas groupby列表中

    给定一个数据框 我想对第一列进行分组 并将第二列作为行中的列表获取 这样数据框如下 a b A 1 A 2 B 5 B 5 B 4 C 6 becomes A 1 2 B 5 5 4 C 6 我该怎么做呢 您可以使用以下方法执行此操作gro
  • 对顺序 SQL 记录进行分组

    寻找一种将连续时钟记录分组到单行中的方法 源系统具有身份列 员工 ID 日期和输入 输出标志 1 输入 2 输出 请注意 ID EmployeeID DATE InOut 1019374 5890 2008 08 19 14 07 14 1
  • 如何在 Pytube 中结合音频和视频?

    我正在尝试编写一段代码 在 Python 3 6 上使用 Pytube 下载 YouTube 视频 但对于大多数视频 渐进式下载 同一文件中的音频和视频 格式最多只能提供 360p 所以我想分别下载音频和视频文件 然后合并起来 我能够下载音
  • 在不更改值顺序的情况下对因子的级别进行重新排序

    我有包含一些数值变量和一些分类变量的数据框factor变量 这些因素的级别顺序不是我想要的方式 numbers lt 1 4 letters lt factor c a b c d df lt data frame numbers lett
  • 合并后,如何跟踪提交的来源?

    我的公司不维护存储库git 我们有效地使用 CVS 但为了我自己的理智 我在本地保留了一个存储库 过去 我想提出与以下相关的提交 bug report abcde 我可以通过 grep 查找提交消息bug report abcde并浏览它们
  • 将 apk 上传到市场时出现错误

    发生意外错误 请稍后再试 是我在 我尝试上传我签名的apk 完成应用程序后 我使用导出签名应用程序工具来生成密钥 为什么我会收到此错误 我发现只需退出并返回即可解决我的问题 使用火狐浏览器
  • 方向更改后未调用 Fragment 的 onActivityResult

    请注意 此问题与以下问题不重复 https stackoverflow com questions 19006776 onactivityresult not working with fragments https stackoverfl
  • Java:地图包含等于或小于另一个地图

    如何检查 1 个子集是否包含小于或等于另一个子集 下面是 SMap 和 TMap 在此示例中 执行方程式将返回 false sMap entrySet containsAll tMap entrySet 我相信它返回 false 因为它试图
  • 带有角度的人类可读日期的时间戳

    是否有内置的角度过滤器将我的unix时间戳转换为人类可读的日期格式 我已经尝试过以下方法 time date medium 但它给出了错误的结果 1232346882 gives Jan 15 1970 7 19 06 AM 我该如何解决这
  • 使用 MSBuild,如何通过迭代 ItemGroup 中的文件来构造动态字符串?

    我需要创建多个 testcontainer 参数以输入到执行 MsTest 的任务中 我有以下内容
  • UIView BringSubviewToFront:*不*将视图带到前面

    我正在实现一个简单的 iOS 纸牌游戏 允许用户以通常的方式拖动纸牌 这些卡片用UIView子类CardView 所有卡片视图都是兄弟视图 它们是子视图SolitaireView 以下代码片段尝试 将卡片置于前面 以便在拖动时它位于所有其他
  • 如何使用 async 和 wait 正确处理

    我正在尝试进行代码替换Thread to Task 睡眠 延迟仅代表长时间运行的活动 static void Main string args ThreadDoWork TaskDoWork public static void Threa
  • 在 WooCommerce 我的帐户页面上隐藏状态为(待付款)的订单

    受到线程的启发 在我的帐户最近订单列表页面隐藏订单状态 https stackoverflow com questions 43392110 hiding order status in my account recent orders l
  • WCF - 在 HTTPS 情况下未使用 HTTP.SYS 正确配置证书。与 Charles 代理一起运行

    这似乎是一个常见错误 还有其他类似问题的帖子 但是 我已经浏览了所有这些帖子和 MSDN 文章 https learn microsoft com en us dotnet framework wcf feature details wor
  • 如何在 Travis CI 上的一个项目中运行 Node.js 和 Ruby 测试

    我有一个包含多个组件的存储库 其中大部分是用 JavaScript Node js 编写的 还有一个是用 Ruby Ruby on Rails 编写的 我想要一个 travis yml 文件来触发一个构建 该构建运行每个组件的所有测试 根据
  • 将 Django 应用程序部署到 Heroku 时收集静态错误

    我正在尝试将 Django 应用程序部署到 Heroku 它开始构建 下载并安装所有内容 但这就是我在收集静态文件时得到的结果 python manage py collectstatic noinput remote Traceback
  • 如何将字符串转换为.net 3.5中的版本?

    我想将 3 5 中创建的软件版本与旧版本进行比较 如果我尝试比较 4 0 中的版本 那么使用以下命令很容易Version Parse但在早期版本中不存在此功能 我尝试使用字符串比较来比较它 但仍然无法获得所需的输出 因为字符串比较不允许我与
  • 使用 MPI 派生数据类型

    我正在学习 Fortran 中的 BCASTing 数据类型 并且有一个代码可以从终端获取两个值并将它们显示在每个进程上 对于整数 整数和整数 实数类型的组合 value1 value2 这是有效的 但是对于整数 实数 8 的组合 它会失败
  • Eclipse Californium CoAP 通配符作为 url 路径

    我正在使用 Eclipse Californium 开发一个 CoAP 应用程序 它将仅显式声明根资源路径 其余资源应通过通配符提供和解析 root 就像在 REST API 或 servlet 上一样 有什么办法可以实现这一点吗 好吧 我