如何定制EOS工作流组织机构?

日期: 2008-05-28 作者:powerise 来源:TechTarget中国

  在基于EOS工作流开发的企业应用中,经常碰到客户的组织机构权限已经统一管理和使用,无法在EOS中直接集成的场景。因此需要对EOS工作流组织机构、角色等进行定制。在本文中描述了定制EOS工作流组织机构、角色的步骤、策略以及要注意的内容。


  2 概述


  2.1 问题或场景


  在基于EOS工作流开发的企业应用中,经常碰到客户的组织机构权限已经统一管理和使用,无法在EOS中直接集成的场景。因此需要对EOS工作流组织机构、角色等进行定制。


  2.2 目的


  在本文中描述了定制EOS工作流组织机构、角色的步骤、策略以及一下要注意的内容。


  2.3 参考资料


  《EOS工作流帮助手册》


  帅小艳: 《EOS工作流和业务结合技术解决方案》


  2.4 工具和技术


  2.5 系统运行环境


  已经在下面环境下测试通过:


  Eos Studio:Version: 5.3,Build id: 0708101429_2857


  数据库:oracle 9.2


  Jdk:1.4.2


  应用服务器:tomcat 5.0.28


  3 总体解决方案


  3.1 工作流组织机构和角色主要Java类


  所有参与者的基类: OMParticipant


  private String id;    //    编号
  private String name;  // 名称
  private String type;  // 类型
  private Map attributeMap;  // 其他属性


  角色参与者类: RoleParticipant extends OMParticipant
  其type属性的值始终为”role”。


  个人参与者类: PersonParticipant extends OMParticipant


  其type属性的值始终为“person”,同时在attributeMap中扩展了四个属性:


  String ATTR_EMAIL = “email”;
  String ATTR_MOBILE = “mobile”;
  String ATTR_PHONE = “phone”;
  String ATTR_POSITION = “position”;


  组织参与者类: OrganizationParticipant extends OMParticipant
  其type属性的值始终为“organization”,同时增加新的属性:


  String orgSEQ;


  岗位参与者类: PositionParticipant extends OMParticipant


  其type属性的值始终为“position”,同时在attributeMap中扩展了一个属性:orgID。


  3.2 EOS工作流组织机构和角色接口


  普元EOS工作流虽然为用户提供了组织机构与角色系统(机构管理),但也支持用户将已有的组织机构加入到普元的工作流应用中。EOS工作流的组织机构模型是层次结构,支持用户、角色、部门、业务机构等实体对象,对于用户可根据自身需求和实际情况进行操作。


  EOS工作流引擎对外部提供了组织机构的Java接口,com.primeton.eos.wf.service.api.WFOMService2,该接口中定义了如下方法:


  /**
     *
     * @function:获取所有角色列表
     *
     * @return RoleParticipant[]
     *
     * @roseuid 3F34BC760137
     *
     */
    public RoleParticipant[] getAllRoles() throws WFOMException;


    /**
     *
     * @function:根据角色ID获取人员列表
     *
     * @param roleID:角色ID
     *
     * @return PersonParticipant
     *
     * @roseuid 3F34BC76013C
     *
     */
    public PersonParticipant[] getPersonByRoleID(String arg0)
            throws WFOMException ;


    /**
     *
     * @function:获取机构信息
     *
     * @param unitID:机构ID
     *
     * @return OrganizationParticipant
     *
     * @roseuid 3F34BC760134
     *
     */
    public OrganizationParticipant findOrganizationByID(String arg0)
            throws WFOMException ;


    /**
     *
     * @function:获取个人参与者
     *
     * @param personID:人员ID
     *
     * @return PersonParticipant
     *
     * @roseuid 3F34BC760130
     *
     */
    public PersonParticipant findPersonByID(String arg0) throws WFOMException {
        PersonParticipant pp = new PersonParticipant();


    /**
     *
     * @function:获取角色信息
     *
     * @param roleID:角色ID
     *
     * @return RoleParticipant
     *
     * @roseuid 3F34BC760132
     *
     */
    public RoleParticipant findRoleByID(String arg0) throws WFOMException ;


    /**
     *
     * @function:获取组织机构的根节点
     *
     * @return OrganizationParticipant
     *
     * @roseuid 3F34BC760138
     *
     */
    public OrganizationParticipant findRootOrganization() throws WFOMException ;


    /**
     *
     * @function:获取机构列表
     *
     * @return OrganizationParticipant[]
     *
     * @roseuid 3F34BC760138
     *
     */
    public OrganizationParticipant[] getAllOrganization() throws WFOMException ;


    /**
     *
     * @function:获取所有机构列表
     *
     * @return OrganizationParticipant[]
     *
     * @roseuid 3F34BC760136
     *
     */
    public OrganizationParticipant[] getAllOrgs(PageCond arg0)
            throws WFOMException ;


    /**
     *
     * @function:获取所有个人列表
     *
     * @return PersonParticipant[]
     *
     * @roseuid 3F34BC760136
     *
     */
    public PersonParticipant[] getAllPerson() throws WFOMException ;


    /**
     *
     * @function:获取所有个人列表
     *
     * @return PersonParticipant[]
     *
     * @roseuid 3F34BC760136
     *
     */
    public PersonParticipant[] getAllPerson(PageCond arg0) throws WFOMException ;


    /**
     *
     * @function:获取所有角色列表
     *
     * @return PersonParticipant[]
     *
     * @roseuid 3F34BC760136
     *
     */
    public RoleParticipant[] getAllRoles(PageCond arg0) throws WFOMException ;


    /**
     *
     * @function:获取指定机构的所有上级机构
     *
     * @return OrganizationParticipant[]
     *
     * @roseuid 3F34BC760136
     *
     */
    public OrganizationParticipant[] getAllSuperiorOrganization(String arg0,
            PageCond arg1) throws WFOMException ;


    /**
     *
     * @function:获取指定机构的直接下属机构列表
     *
     * @param unitID:机构ID
     *
     * @return OrganizationParticipant
     *
     * @roseuid 3F34CA930157
     *
     */
    public OrganizationParticipant[] getJuniorOrganization(String arg0)
            throws WFOMException ;


    /**
     *
     * @function:获取人员所属机构
     *
     * @param personID:人员Id
     *
     * @return OrganizationParticipant
     *
     * @roseuid 3F34BC76013E
     *
     */
    public OrganizationParticipant[] getOrganizationByPersonID(String arg0)
            throws WFOMException ;


    /**
     *
     * @function:通过机构Id获取人员列表
     *
     * @param unitID:机构id
     *
     * @return PersonParticipant
     *
     * @roseuid 3F34BC760140
     *
     */
    public PersonParticipant[] getPersonByOrganizationID(String arg0)
            throws WFOMException ;


    /**
     *
     * @function:通过机构Id获取人员列表
     *
     * @param unitID:机构id
     *
     * @return PersonParticipant
     *
     * @roseuid 3F34BC760140
     *
     */
    public PersonParticipant[] getPersonByOrganizationID(String arg0,
            PageCond arg1) throws WFOMException ;


    /**
     *
     * @function:根据人员ID获取角色列表
     *
     * @param personID:人员ID
     *
     * @return RoleParticipant
     *
     * @roseuid 3F34BC76013A
     *
     */
    public RoleParticipant[] getRolesByPersonID(String arg0)
            throws WFOMException ;


    /**
     *
     * @function:根据组织ID获取其上级组织信息
     *
     * @param arg0:组织ID
     *
     * @return OrganizationParticipant
     *
     * @roseuid 3F34BC76013A
     *
     */
    public OrganizationParticipant getSuperiorOrganization(String arg0)
            throws WFOMException ;


    /**
     *
     * @function:获取岗位信息
     *
     * @param arg0:岗位ID
     *
     * @return PositionParticipant
     *
     * @roseuid 3F34BC760132
     *
     */
    public PositionParticipant findPositionParticipant(String arg0)
            throws WFOMException ;


    /**
     *
     * @function:获取指定岗位下的所有人员
     *
     * @param arg0:岗位ID
     *
     * @return PersonParticipant[]
     *
     * @roseuid 3F34BC760132
     *
     */
    public PersonParticipant[] getPersonsByPositionID(String arg0)
            throws WFOMException ;


    /**
     *
     * @function:获取某机构下的所有职务
     *
     * @param unitID:机构ID
     *
     * @return ParticipantList
     *
     * @roseuid 3F34C56802AF
     *
     */
    public PositionParticipant[] getPositionsByOrganizationID(String arg0)
            throws WFOMException ;


    /**
     *
     * @function:获取指定人员的所有岗位
     *
     * @param arg0:人员ID
     *
     * @return PositionParticipant[]
     *
     * @roseuid 3F34C56802AF
     *
     */
    public PositionParticipant[] getPositionsByPersonID(String arg0)
            throws WFOMException ;


    public OrganizationParticipant[] queryOrgs(Element arg0)
            throws WFOMException ;


    public PersonParticipant[] queryPersons(Element arg0) throws WFOMException ;


    public PositionParticipant[] queryPositions(Element arg0)
            throws WFOMException ;


    public RoleParticipant[] queryRoles(Element arg0) throws WFOMException ;


  3.3 如何定制EOS组织机构和角色


  3.3.1 提供组织机构和角色实现


  EOS工作流中提供了组织机构和角色接口,每个要定制组织机构和角色的企业都必须先为该接口提供满足自己实际业务需要的实现。


  需要说明的是,该接口的实现类并不是需要为每一个方法都提供具体实现,如果业务上不需要的方法,我们可以提供一种空实现即可,比如某个企业的组织机构和角色部分不需要采用岗位,我们就可以将那些和岗位相关的接口提供空实现。比如:
  public PositionParticipant findPositionParticipant(String arg0)
            throws WFOMException {
        // TODO 自动生成方法存根
        return null;
}


  3.3.1.1 一个实现了组织机构和角色接口的例子


  下面是一个简单的组织机构和角色的实现,它根据实现类中的几个数组来处理系统的组织机构、角色,不包含对岗位的支持。


  public class NQOMServiceImpl implements WFOMService2 {
    private String[] roles = new String[] { “role1”, “role2” };


    private String[] users = new String[] { “user1”, “user2” };


    private String[] userRoles = new String[] { “user1,role1,role2”,
            “user2,role2” };


    private String[] orgs = new String[] { “org1,999999”, “org2,org1”,
            “org3,org1” };


    private String[] userOrgs = new String[] { “user1,org1”, “user2,org2” };


    /**
     *
     * @function:获取所有角色列表
     *
     * @return RoleParticipant[]
     *
     * @roseuid 3F34BC760137
     *
     */
    public RoleParticipant[] getAllRoles() throws WFOMException {
        RoleParticipant[] rps = new RoleParticipant[roles.length];


        for (int i = 0; i < roles.length; i++) {
            RoleParticipant rp = new RoleParticipant();
            rp.setID(roles[i]);
            rp.setName(roles[i]);
            rp.setType(DefineConst.PARTICIPANTINFO_PARTICIPANTLIST_TYPE_ROLE);


            rps[i] = rp;
            rp = null;
        }


        return rps;
    }


    /**
     *
     * @function:根据角色ID获取人员列表
     *
     * @param roleID:角色ID
     *
     * @return PersonParticipant
     *
     * @roseuid 3F34BC76013C
     *
     */
    public PersonParticipant[] getPersonByRoleID(String arg0)
            throws WFOMException {
        List ppsList = new ArrayList();


        for (int i = 0; i < userRoles.length; i++) {
            if (userRoles[i].indexOf(arg0) > -1) {
                String userName = userRoles[i].substring(0, userRoles[i]
                        .indexOf(“,”));


                PersonParticipant pp = new PersonParticipant();


                pp.setID(userName);
                pp.setName(userName);
                pp
                        .setType(DefineConst.PARTICIPANTINFO_PARTICIPANTLIST_TYPE_PERSON);


                ppsList.add(pp);
                pp = null;
            }
        }


        PersonParticipant[] pps = new PersonParticipant[ppsList.size()];
        ppsList.toArray(pps);


        return pps;
    }


    /**
     *
     * @function:获取机构信息
     *
     * @param unitID:机构ID
     *
     * @return OrganizationParticipant
     *
     * @roseuid 3F34BC760134
     *
     */
    public OrganizationParticipant findOrganizationByID(String arg0)
            throws WFOMException {
        OrganizationParticipant op = new OrganizationParticipant();


        for (int i = 0; i < orgs.length; i++) {
            String orgName = orgs[i].substring(0, orgs[i].indexOf(“,”));


            if (orgName.equals(arg0)) {
                op.setID(orgName);
                op.setName(orgName);
                op
                        .setType(DefineConst.PARTICIPANTINFO_PARTICIPANTLIST_TYPE_ORGANIZATION);


                break;
            }
        }
        return op;
    }


    /**
     *
     * @function:获取个人参与者
     *
     * @param personID:人员ID
     *
     * @return PersonParticipant
     *
     * @roseuid 3F34BC760130
     *
     */
    public PersonParticipant findPersonByID(String arg0) throws WFOMException {
        PersonParticipant pp = new PersonParticipant();


        for (int i = 0; i < users.length; i++) {
            if (users[i].equals(arg0)) {
                pp.setID(users[i]);
                pp.setName(users[i]);
                pp
                        .setType(DefineConst.PARTICIPANTINFO_PARTICIPANTLIST_TYPE_PERSON);


                break;
            }
        }
        return pp;
    }


    /**
     *
     * @function:获取角色信息
     *
     * @param roleID:角色ID
     *
     * @return RoleParticipant
     *
     * @roseuid 3F34BC760132
     *
     */
    public RoleParticipant findRoleByID(String arg0) throws WFOMException {
        RoleParticipant rp = new RoleParticipant();


        for (int i = 0; i < roles.length; i++) {
            if (roles[i].equals(arg0)) {
                rp.setID(roles[i]);
                rp.setName(roles[i]);
                rp
                        .setType(DefineConst.PARTICIPANTINFO_PARTICIPANTLIST_TYPE_ROLE);


                break;
            }
        }
        return rp;
    }


    /**
     *
     * @function:获取组织机构的根节点
     *
     * @return OrganizationParticipant
     *
     * @roseuid 3F34BC760138
     *
     */
    public OrganizationParticipant findRootOrganization() throws WFOMException {
        OrganizationParticipant op = new OrganizationParticipant();


        for (int i = 0; i < orgs.length; i++) {
            String orgName = orgs[i].substring(orgs[i].indexOf(“,”) + 1);


            if (orgName.equals(“999999”)) {
                op.setID(“999999”);
                op.setName(“上海普元”);
                op
                        .setType(DefineConst.PARTICIPANTINFO_PARTICIPANTLIST_TYPE_ORGANIZATION);


                break;
            }
        }
        return op;
    }


    /**
     *
     * @function:获取机构列表
     *
     * @return OrganizationParticipant[]
     *
     * @roseuid 3F34BC760138
     *
     */
    public OrganizationParticipant[] getAllOrganization() throws WFOMException {
        OrganizationParticipant[] ops = new OrganizationParticipant[roles.length];


        for (int i = 0; i < orgs.length; i++) {
            OrganizationParticipant op = new OrganizationParticipant();
            op.setID(orgs[i]);
            op.setName(orgs[i]);
            op
                    .setType(DefineConst.PARTICIPANTINFO_PARTICIPANTLIST_TYPE_ORGANIZATION);


            ops[i] = op;
            op = null;
        }


        return ops;
    }


    /**
     *
     * @function:获取所有机构列表
     *
     * @return OrganizationParticipant[]
     *
     * @roseuid 3F34BC760136
     *
     */
    public OrganizationParticipant[] getAllOrgs(PageCond arg0)
            throws WFOMException {
        // TODO 自动生成方法存根
        return null;
    }


    /**
     *
     * @function:获取所有个人列表
     *
     * @return PersonParticipant[]
     *
     * @roseuid 3F34BC760136
     *
     */
    public PersonParticipant[] getAllPerson() throws WFOMException {
        PersonParticipant[] pps = new PersonParticipant[roles.length];


        for (int i = 0; i < users.length; i++) {
            PersonParticipant pp = new PersonParticipant();
            pp.setID(users[i]);
            pp.setName(users[i]);
            pp.setType(DefineConst.PARTICIPANTINFO_PARTICIPANTLIST_TYPE_PERSON);


            pps[i] = pp;
            pp = null;
        }


        return pps;
    }


    /**
     *
     * @function:获取所有个人列表
     *
     * @return PersonParticipant[]
     *
     * @roseuid 3F34BC760136
     *
     */
    public PersonParticipant[] getAllPerson(PageCond arg0) throws WFOMException {
        // TODO 自动生成方法存根
        return null;
    }


    /**
     *
     * @function:获取所有角色列表
     *
     * @return PersonParticipant[]
     *
     * @roseuid 3F34BC760136
     *
     */
    public RoleParticipant[] getAllRoles(PageCond arg0) throws WFOMException {
        // TODO 自动生成方法存根
        return null;
    }


    /**
     *
     * @function:获取指定机构的所有上级机构
     *
     * @return OrganizationParticipant[]
     *
     * @roseuid 3F34BC760136
     *
     */
    public OrganizationParticipant[] getAllSuperiorOrganization(String arg0,
            PageCond arg1) throws WFOMException {
        // TODO 自动生成方法存根
        return null;
    }


    /**
     *
     * @function:获取指定机构的直接下属机构列表
     *
     * @param unitID:机构ID
     *
     * @return OrganizationParticipant
     *
     * @roseuid 3F34CA930157
     *
     */
    public OrganizationParticipant[] getJuniorOrganization(String arg0)
            throws WFOMException {
        List opsList = new ArrayList();


        for (int i = 0; i < orgs.length; i++) {
            String parentOrgName = orgs[i].substring(orgs[i].indexOf(“,”) + 1);
            String orgName = orgs[i].substring(0, orgs[i].indexOf(“,”));
            if (parentOrgName.equals(arg0)) {
                OrganizationParticipant op = new OrganizationParticipant();
                op.setID(orgName);
                op.setName(orgName);
                op
                        .setType(DefineConst.PARTICIPANTINFO_PARTICIPANTLIST_TYPE_ORGANIZATION);


                opsList.add(op);


                op = null;
            }
        }


        OrganizationParticipant[] ops = new OrganizationParticipant[opsList
                .size()];
        opsList.toArray(ops);
        return ops;
    }


    /**
     *
     * @function:获取人员所属机构
     *
     * @param personID:人员Id
     *
     * @return OrganizationParticipant
     *
     * @roseuid 3F34BC76013E
     *
     */
    public OrganizationParticipant[] getOrganizationByPersonID(String arg0)
            throws WFOMException {
        // TODO 自动生成方法存根
        return null;
    }


    /**
     *
     * @function:通过机构Id获取人员列表
     *
     * @param unitID:机构id
     *
     * @return PersonParticipant
     *
     * @roseuid 3F34BC760140
     *
     */
    public PersonParticipant[] getPersonByOrganizationID(String arg0)
            throws WFOMException {
        // TODO 自动生成方法存根
        return null;
    }


    /**
     *
     * @function:通过机构Id获取人员列表
     *
     * @param unitID:机构id
     *
     * @return PersonParticipant
     *
     * @roseuid 3F34BC760140
     *
     */
    public PersonParticipant[] getPersonByOrganizationID(String arg0,
            PageCond arg1) throws WFOMException {
        // TODO 自动生成方法存根
        return null;
    }


    /**
     *
     * @function:根据人员ID获取角色列表
     *
     * @param personID:人员ID
     *
     * @return RoleParticipant
     *
     * @roseuid 3F34BC76013A
     *
     */
    public RoleParticipant[] getRolesByPersonID(String arg0)
            throws WFOMException {
        // TODO 自动生成方法存根
        return null;
    }


    /**
     *
     * @function:根据组织ID获取其上级组织信息
     *
     * @param arg0:组织ID
     *
     * @return OrganizationParticipant
     *
     * @roseuid 3F34BC76013A
     *
     */
    public OrganizationParticipant getSuperiorOrganization(String arg0)
            throws WFOMException {
        // TODO 自动生成方法存根
        return null;
    }


    /**
     *
     * @function:获取岗位信息
     *
     * @param arg0:岗位ID
     *
     * @return PositionParticipant
     *
     * @roseuid 3F34BC760132
     *
     */
    public PositionParticipant findPositionParticipant(String arg0)
            throws WFOMException {
        // TODO 自动生成方法存根
        return null;
    }


    /**
     *
     * @function:获取指定岗位下的所有人员
     *
     * @param arg0:岗位ID
     *
     * @return PersonParticipant[]
     *
     * @roseuid 3F34BC760132
     *
     */
    public PersonParticipant[] getPersonsByPositionID(String arg0)
            throws WFOMException {
        // TODO 自动生成方法存根
        return null;
    }


    /**
     *
     * @function:获取某机构下的所有职务
     *
     * @param unitID:机构ID
     *
     * @return ParticipantList
     *
     * @roseuid 3F34C56802AF
     *
     */
    public PositionParticipant[] getPositionsByOrganizationID(String arg0)
            throws WFOMException {
        // TODO 自动生成方法存根
        return null;
    }


    /**
     *
     * @function:获取指定人员的所有岗位
     *
     * @param arg0:人员ID
     *
     * @return PositionParticipant[]
     *
     * @roseuid 3F34C56802AF
     *
     */
    public PositionParticipant[] getPositionsByPersonID(String arg0)
            throws WFOMException {
        // TODO 自动生成方法存根
        return null;
    }


    public OrganizationParticipant[] queryOrgs(Element arg0)
            throws WFOMException {
        // TODO 自动生成方法存根
        return null;
    }


    public PersonParticipant[] queryPersons(Element arg0) throws WFOMException {
        // TODO 自动生成方法存根
        return null;
    }


    public PositionParticipant[] queryPositions(Element arg0)
            throws WFOMException {
        // TODO 自动生成方法存根
        return null;
    }


    public RoleParticipant[] queryRoles(Element arg0) throws WFOMException {
        // TODO 自动生成方法存根
        return null;
    }
}


  3.3.2 将定制的组织机构、角色实现配置到EOS工作流容器中


  则打开$EOS_HOME/config/wfconfig.xml,找到下面的配置信息,并设置为如下红色部分


  <group name=”ServiceLocator”>
  <!– com.primeton.eos.service.OmServiceImple2为组织模型实现类–>
  <configValue key=”WFOMSERVICEIMPL”>
  com.primeton.eos.service.OmServiceImple2
  </configValue>
  </group>   


  3.3.3 将定制的组织机构和角色加入到EOS Studio中


  在EOS studio中内部启动一个项目,该项目对应的EOS Server已经按照3.3.2中的步骤将定制的组织机构和角色配置到了EOS工作流中。


  在studio打开组织机构角色视图,点击右键“刷新”按钮刷新组织机构和角色
[注]:如果定义的组织机构、角色、用户比较多的情况下,会导致刷新时出错(studio通过调用server中webservice获取,数据量比较大的情况下studio的jvm内存不够),所以,可看情况是否需要将所有信息都刷新过来。这些配置信息是在wfconfig.xml中:


  <group name=”OrgModel”>
            <configValue key=”PERSON”>false</configValue>        //刷新到人
            <configValue key=”ROLE”>true</configValue>            //刷新到角色
            <configValue key=”ROLE_PERSON”>true</configValue>    //刷新到角色-人
            <configValue key=”ORGANIZATION”>true</configValue>//刷新到机构
            <configValue key=”ORG_PERSON”>true</configValue>    //刷新到机构-人
            <configValue key=”ORG_POSITION”>true</configValue>//刷新到机构-岗位
            <configValue key=”POSITION_PERSON”>true</configValue>//刷新到岗位-人
        </group>


  以上定义true表明刷新,false表明不刷新,修改此配置文件之后需要重新启动server


  3.3.4 在EOS工作流中应用新的组织机构和角色


  通过上面的步骤后,在工作流程(EOS Studio中)的人工活动的参与者设置中,在组织机构与角色一项中选择添加组织机构和角色就能够看到已经设置的组织和角色了。


  原文出处:http://gocom.primeton.com/blog8892_1394.htm

我们一直都在努力坚持原创.......请不要一声不吭,就悄悄拿走。

我原创,你原创,我们的内容世界才会更加精彩!

【所有原创内容版权均属TechTarget,欢迎大家转发分享。但未经授权,严禁任何媒体(平面媒体、网络媒体、自媒体等)以及微信公众号复制、转载、摘编或以其他方式进行使用。】

微信公众号

TechTarget微信公众号二维码

TechTarget

官方微博

TechTarget中国官方微博二维码

TechTarget中国

作者

powerise
powerise

相关推荐

  • API创建影响生产的六个方面

    在API创建方面,简单性至关重要。AnyPresence的Vivek Gupta讨论了开发者可以从6个方面处理好API的创建问题,从而加速API生产。

  • 微服务:是谁看上了这块小鲜肉

    微服务——IT领域的又一个新名词。但它是否能如同OpenStack,如同Docker那样成为众人疯抢的“肥肉”呢?从目前来看,可能还没有到达疯抢的地步,但也不乏支持者。

  • 应用开发工具帮助报社与时俱进

    新闻媒体业务要一直向顶尖技术看齐,如果他们想要打败竞争对手,成为社会的脉搏的话。心态一直是最重要的,无论是在收集和报道新闻方面,还是在内部运营方法。

  • 为移动工作者赋权构建API及工作流的步骤

    主管不能简单地把移动工作者认为是不坐在一起的人。相反,赋权要从评估员工需求开始,因为接下来关键的速度爆发当然就必须来自于移动设备和宽带服务的利用。