Exemple #1
0
    def get(self, id):
        """Get all data, getall
        """
        # check the request is validtion,
        # ex: we not allow request arg 'itemsPerPage1'

        validSet = set(field_inputs_wrap.keys())
        requestArgsSet = set(request.dataDictWrap.keys())

        if not ExtraParamsIsValid(requestArgsSet, validSet):
            return omitError(
                ErrorMsg=repr(requestArgsSet.difference(validSet))), 400

        # one to many
        # 1. parsing reqest
        try:
            for k, v in field_inputs.items():
                field_inputs[k]['required'] = False

            orgArgs, self.args = GetRequestArgs(
                None, field_inputs_wrap,
                dict((col, request.args.get(col)) for col in request.args))
            # get default value
            # print(self.args, 'self.args', resource_fields_wrap)
            self.response = dict(
                marshal(self.args, resource_fields_wrap).items())

            self.args[__heads__] = []
        except Exception as error:
            logger.debug('traceback.format_exc(%s)', traceback.format_exc())

            return omitError(ErrorMsg=repr(error)), 400

        if not hasattr(g, 'user'):
            return omitError('CE_NOT_EXIST', 'not login yet'), 400

        r = g.user
        if r is None:
            return omitError('CE_NOT_EXIST'), 400

        # 1.1 check permission
        if r.id != id:
            return omitError('CE_UNAUTHORIZED', 'id not match'), 400

        # 2. export to user
        _r = dict((col, getattr(r, col)) for col in r.__table__.columns.keys())
        self.args[field_inputs_wrap_head] = _r

        _resource_fields = resource_fields.copy()
        _resource_fields_wrap = resource_fields_wrap.copy()
        for col in resource_fields_wrap:
            if col not in ['type', 'subtype']:
                _resource_fields_wrap.pop(col, None)

        _resource_fields.pop('access_token', None)
        _resource_fields_wrap[field_inputs_wrap_head] = (
            fields.Nested(_resource_fields))
        self.args['type'] = "system"
        self.args['subtype'] = "regist"
        return marshal(self.args, _resource_fields_wrap), 200
Exemple #2
0
    def get(self):
        """Get all data
        """
        # one to many
        # 1. parsing reqest
        try:
            # FIXME:
            # when i assign field_inputs['name']['required'] to True,
            # it could through below error:
            # ValueError: [name]: (name Valid Error) Missing required parameter
            # in dataDict
            # but i have no idea what it happen.
            if os.environ.get('EVN'):
                # in unit test
                field_inputs['name']['required'] = False
                logger.warning('now we are in unit test mode, turn off'\
                               ' field_inputs[\'name\'][\'required\']'\
                               ' but 1st run is ok :(')

            self.args = GetRequest(
                None, field_inputs_wrap,
                dict((col, request.args.get(col)) for col in request.args))
            # get default value
            self.response = dict(
                marshal(self.args, resource_fields_wrap).items())

            self.args[__heads__] = []
        except Exception as error:
            logger.debug('traceback.format_exc(%s)', traceback.format_exc())

            return omitError(ErrorMsg=repr(error)), 400

        itemsPerPage = self.response['itemsPerPage']
        page = self.response['page']
        orderBy = getattr(grp, self.response['orderBy'])
        isDesc = getattr(orderBy, 'desc' if self.response['desc'] else 'asc')

        r = grp.query.order_by(isDesc())
        _r = r.all()
        self.args['total'] = len(_r)

        if itemsPerPage is not 0:
            _r = r.offset(itemsPerPage * (page-1))\
                    .limit(itemsPerPage)\
                    .all()
        r = _r

        # 2. export to user
        data, field = SerialGroupOutput(r,
                                        resource_fields=resource_fields,
                                        omitKeys=['id', 'name'])
        self.args[__heads__] = data

        _resource_fields_wrap = resource_fields_wrap.copy()
        _resource_fields_wrap[__heads__] = fields.List(fields.Nested(field))

        return marshal(self.args, _resource_fields_wrap), 200
Exemple #3
0
    def get(self, id):
        """Get all data, getall
        """
        # check the request is validtion,
        # ex: we not allow request arg 'itemsPerPage1'

        validSet = set(field_inputs_wrap.keys())
        requestArgsSet = set(request.dataDictWrap.keys())

        if not ExtraParamsIsValid(requestArgsSet, validSet):
            return omitError(
                ErrorMsg=repr(requestArgsSet.difference(validSet))), 400

        # one to many
        # 1. parsing reqest
        try:
            for k, v in field_inputs.items():
                field_inputs[k]['required'] = False

            orgArgs, self.args = GetRequestArgs(
                None, field_inputs_wrap,
                dict((col, request.args.get(col)) for col in request.args))
            # get default value
            # print(self.args, 'self.args', resource_fields_wrap)
            self.response = dict(
                marshal(self.args, resource_fields_wrap).items())

            self.args[__heads__] = []
        except Exception as error:
            logger.debug('traceback.format_exc(%s)', traceback.format_exc())

            return omitError(ErrorMsg=repr(error)), 400

        r = obj.query.filter(obj.id == id, obj.isdel == False).scalar()
        if r is None:
            return omitError('CE_NOT_EXIST', 'id {} not found'.format(id)), 400

        # 2. export to user
        _r = dict((col, getattr(r, col)) for col in r.__table__.columns.keys())
        self.args[field_inputs_wrap_head] = _r

        _resource_fields = resource_fields.copy()
        _resource_fields_wrap = resource_fields_wrap.copy()
        for col in resource_fields_wrap:
            if col not in ['type', 'subtype']:
                _resource_fields_wrap.pop(col, None)

        _resource_fields_wrap[field_inputs_wrap_head] = (
            fields.Nested(_resource_fields))
        self.args['type'] = "business"
        self.args['subtype'] = "rate"
        return marshal(self.args, _resource_fields_wrap), 200
Exemple #4
0
    def put(self, id):
        requestArgsSet = set((col) for col in request.args)
        if not ExtraParamsIsValid(requestArgsSet):
            return omitError(ErrorMsg=repr(set(
                (col) for col in request.args))), 400

        try:
            self.dataDict = request.get_json()
            request.dataDict = self.dataDict[__head__]
            add_argument(_reqparse, field_inputs)
            self.args = _reqparse.parse_args()
        except Exception as error:
            logger.debug('traceback.format_exc(%s)', traceback.format_exc())

            if error == type(BadRequest):
                return omitError(ErrorMsg='maybe json format error'), 400

            return omitError(ErrorMsg='{}'.format(repr(error.args))), 400

        try:
            checkInputIsValid(self.args)
        except Exception as error:
            return error.args

        r = obj.query.filter(obj.id == id).scalar()
        for k, v in self.args.items():
            if v != None:
                setattr(r, k, v)

        db.session.add(r)

        try:
            db.session.flush()
            db.session.commit()
        except Exception as error:
            db.session.rollback()
            logger.warning('session commit error(%s)', error)

            if exc.IntegrityError == type(error):
                return omitError('CE_NAME_CONFLICT', repr(error)), 400

            return omitError(ErrorMsg=repr(error)), 400

        self.args[__head__] = {}
        _resource_fields_wrap = {}
        _resource_fields_wrap[__head__] = fields.Nested(resource_fields)

        for col in r.__table__.columns.keys():
            self.args[__head__][col] = getattr(r, col)

        return marshal(self.args, _resource_fields_wrap), 200
Exemple #5
0
    def get(self):
        # check the request is validtion,
        # ex: we not allow request arg 'itemsPerPage1'

        validSet = set(__heads__, 'refBy')
        requestArgsSet = set(request.dataDictWrap.keys())

        if not ExtraParamsIsValid(requestArgsSet, validSet):
            return omitError(
                ErrorMsg=repr(requestArgsSet.difference(validSet))), 400

        try:
            self.args = _reqparse.parse_args()
            self.response = dict(
                marshal(self.args, resource_fields_wrap).items())
            self.args[__heads__] = []

        except Exception as error:
            logger.debug('traceback.format_exc(%s)', traceback.format_exc())
            return omitError('CE_INVALID_PARAM', repr(error)), 400

        itemsPerPage = self.response['itemsPerPage']
        page = self.response['page']
        orderBy = getattr(obj, self.response['orderBy'])
        isDesc = getattr(orderBy, 'desc' if self.response['desc'] else 'asc')

        # .order_by(User.login.desc())
        r = obj.query.order_by(isDesc())

        if itemsPerPage is 0:
            r = r.all()
        else:
            r = r.offset(itemsPerPage * (page-1))\
                    .limit(itemsPerPage)\
                    .all()
        for _r in r:
            __r = dict(
                (col, getattr(_r, col)) for col in _r.__table__.columns.keys())
            self.args[__heads__].append(__r)

        self.args['total'] = len(r)

        _resource_fields_wrap[__heads__] = {}
        _resource_fields_wrap[__heads__] = fields.List(
            fields.Nested(resource_fields))
        return marshal(self.args, _resource_fields_wrap), 200
Exemple #6
0
    def get(self, id):

        requestArgsSet = set((col) for col in request.args)
        if not ExtraParamsIsValid(requestArgsSet):
            return omitError(ErrorMsg=repr(set(
                (col) for col in request.args))), 400

        r = obj.query.filter(obj.id == id).scalar()

        if r is None:
            return omitError('CE_NOT_EXIST',
                             'user id {} not found'.format(id)), 400

        self.args = {}
        self.args[__head__] = {}
        _resource_fields_wrap = {}
        _resource_fields_wrap[__head__] = fields.Nested(resource_fields)

        for col in r.__table__.columns.keys():
            self.args[__head__][col] = getattr(r, col)

        return marshal(self.args, _resource_fields_wrap), 200
Exemple #7
0
def signin(user):
    g.user = user
    _resource_fields = {}
    _resource_fields_wrap = resource_fields_wrap.copy()
    for col in resource_fields_wrap:
        if col not in ['type', 'subtype']:
            _resource_fields_wrap.pop(col, None)

    _resource_fields_wrap[field_inputs_wrap_head] = fields.Nested(
        resource_fields)

    args = {}
    args[field_inputs_wrap_head] = dict(
        (col, getattr(user, col)) for col in user.__table__.columns.keys())
    token = user.generate_auth_token()
    args[field_inputs_wrap_head]['access_token'] = token.decode('ascii')
    args[field_inputs_wrap_head]['clientIp'] = request.environ['REMOTE_ADDR']

    logger.debug("args[field_inputs_wrap_head]: %s",
                 args[field_inputs_wrap_head])
    args['type'] = "admin"
    args['subtype'] = "login"

    return args, _resource_fields_wrap
Exemple #8
0
                argument=['name', 'type', 'description'],
                )

resource_fields, resource_fields_ref, resource_fields_wrap = GetResource(
    field_inputs, field_inputs_ref, field_inputs_wrap, __heads__)

# not extend to resource_fields
field_inputs['name']['required'] = True
field_inputs[__obj__heads__] = {
    'type': {
        fields.List(
            fields.Nested({
                'id': {
                    'type': fields.Integer(),
                    'required': True
                },
                'name': {
                    'type': fields.String()
                }
            }))
    }
}


class ObjectIpgroup(Resource):
    """
        entry point about '/rest/objects/ipgroups/<int:id>'
        when user do below actions:
        getone/put
    """
    def __init__(self):
Exemple #9
0
    def get(self):
        """Get all data, getall

         @api {get} /rest/objects/ipaddrs Read IP Addresses
         @apiVersion 0.0.1
         @apiName GetIpAddrs
         @apiVersion 0.0.1
         @apiGroup objects
         @apiPermission registered user
         
         @apiDescription
         todo validation
         
         @apiParam {Number=0, 25, 50, 100} [itemsPerPage=25] items for each request.
         @apiParam {Number} [page=1] page you want to request from, start with 1.
         @apiParam {String="name", "description"} [orderBy=name] the items order by column you specified.
         @apiParam {String="true", "false"} [desc=false] the items order by descending or asceding order.

         
         @apiExample Example usage:
         curl -i http://localhost/rest/objects/ipaddrs?itemsPerPage=50&page=1&orderBy=name&desc=true
         
         @apiSuccess {Number}   total         total items for pagination.
         @apiSuccess {String}   orderBy       the items order by column you specified.
         @apiSuccess {Number}   page          page you want to request from, start with 1.
         @apiSuccess {Number}   itemsPerPage  items for each request.
         @apiSuccess {String}   desc          the items order by descending or asceding order.
         @apiSuccess {Object[]} ipaddrs       List of IP Addresses.
         @apiSuccess {String}   ipaddrs.addr1 1st IP Address.
         @apiSuccess {String}   ipaddrs.addr2 2ed IP Address.
         @apiSuccess {String}   ipaddrs.description this items's description.
         @apiSuccess {Number}   ipaddrs.id index in database.
         @apiSuccess {String}   ipaddrs.ipVersion IP Address version.
         @apiSuccess {String}   ipaddrs.name items uniq name for record.
         @apiSuccess {String}   ipaddrs.type IP Address type, the possible values are 'Single', 'Range', 'Subnet'.

         @apiError CE_INVALID_PARAM invalid parameter
         @api {get} /rest/objects/ipaddrs
         @apiErrorExample {json} we use invalid parameter pages
            curl -i http://localhost/rest/objects/ipaddrs?pages=1
            ================================================
             HTTP/1.0 400 BAD REQUEST
            {
                "errorId": 2001,
                "message": "{'pages'}"
            }
        """
        # check the request is validtion,
        # ex: we not allow request arg 'itemsPerPage1'

        validSet = set(field_inputs_wrap.keys())
        requestArgsSet = set(request.dataDictWrap.keys())

        if not ExtraParamsIsValid(requestArgsSet, validSet):
            return omitError(
                ErrorMsg=repr(requestArgsSet.difference(validSet))), 400

        # one to many
        # 1. parsing reqest
        try:
            # FIXME:
            # when i assign field_inputs['name']['required'] to True,
            # it could through below error:
            # ValueError: [name]: (name Valid Error) Missing required parameter
            # in dataDict
            # but i have no idea what it happen.
            if os.environ.get('EVN'):
                # in unit test
                field_inputs['name']['required'] = False
                logger.warning('now we are in unit test mode, turn off'\
                               ' field_inputs[\'name\'][\'required\']'\
                               ' but 1st run is ok :(')

            orgArgs, self.args = GetRequestArgs(
                None, field_inputs_wrap,
                dict((col, request.args.get(col)) for col in request.args))
            # get default value
            # print(self.args, 'self.args', resource_fields_wrap)
            self.response = dict(
                marshal(self.args, resource_fields_wrap).items())

            self.args[__heads__] = []
        except Exception as error:
            logger.debug('traceback.format_exc(%s)', traceback.format_exc())

            return omitError(ErrorMsg=repr(error)), 400

        itemsPerPage = self.response['itemsPerPage']
        page = self.response['page']
        orderBy = getattr(obj, self.response['orderBy'])
        isDesc = getattr(orderBy, 'desc' if self.response['desc'] else 'asc')

        r = obj.query.order_by(isDesc())
        _r = r.all()
        self.args['total'] = len(_r)

        if itemsPerPage is not 0:
            _r = r.offset(itemsPerPage * (page-1))\
                    .limit(itemsPerPage)\
                    .all()

        r = _r
        # 2. export to user
        for _r in r:
            __r = dict(
                (col, getattr(_r, col)) for col in _r.__table__.columns.keys())
            self.args[__heads__].append(__r)

        resource_fields_wrap[__heads__] = fields.List(
            fields.Nested(resource_fields))
        return marshal(self.args, resource_fields_wrap), 200
Exemple #10
0
    def get(self, id):
        """
        @api {get} /rest/objects/ipaddr/:id get one IP address item.
        @apiName GetIpAddr
        @apiVersion 0.0.1
        @apiGroup objects
        @apiPermission registered user
        
        @apiDescription
        todo validation
        
        @apiParam {Number} id IP Address item id.

        @apiExample Example usage:
        curl -i http://localhost/rest/objects/ipaddr/7
         
        @apiSuccess {Object[]} ipaddrs       List of IP Addresses.
        @apiSuccess {String}   ipaddrs.addr1 1st IP Address.
        @apiSuccess {String}   ipaddrs.addr2 2ed IP Address.
        @apiSuccess {String}   ipaddrs.description this items's description.
        @apiSuccess {Number}   ipaddrs.id index in database.
        @apiSuccess {String}   ipaddrs.ipVersion IP Address version.
        @apiSuccess {String}   ipaddrs.name items uniq name for record.
        @apiSuccess {String}   ipaddrs.type IP Address type, the possible values are 'Single', 'Range', 'Subnet'.

        @apiError CE_INVALID_PARAM invalid parameter
        @api {get} /rest/objects/ipaddr/:id
        @apiErrorExample {json} we use invalid parameter pages
            curl -X GET -H "mTag: xx" -H "Content-Type:application/json" -d "${BODY}" http://localhost/rest/objects/ipaddr/7?pages=1
            ================================================
            HTTP/1.0 400 BAD REQUEST
           {
               "errorId": 2001,
               "message": "{'pages'}"
           }
        
        @apiError CE_NOT_EXIST item not found
        @api {get} /rest/objects/ipaddr/:id
        @apiErrorExample {json} we use not exist id
            curl -X GET -H "mTag: xx" -H "Content-Type:application/json" -d "${BODY}" http://localhost/rest/objects/ipaddr/17
            ================================================
            HTTP/1.0 400 BAD REQUEST
           {
               "errorId": 2003,
               "message": "id 17 not found"
           }

        """
        requestArgsSet = set((col) for col in request.args)
        if not ExtraParamsIsValid(requestArgsSet):
            return omitError(ErrorMsg=repr(set(
                (col) for col in request.args))), 400

        r = obj.query.filter(obj.id == id).scalar()

        if r is None:
            return omitError('CE_NOT_EXIST', 'id {} not found'.format(id)), 400

        self.args = {}
        self.args[__head__] = {}
        _resource_fields_wrap = {}
        _resource_fields_wrap[__head__] = fields.Nested(resource_fields)

        for col in r.__table__.columns.keys():
            self.args[__head__][col] = getattr(r, col)

        return marshal(self.args, _resource_fields_wrap), 200
Exemple #11
0
    def get(self):
        """Get all data, getall

        @api {get} /rest/customer/businesses list business
        @apiName GetAllCustomerBusinesses
        @apiVersion 0.0.3
        @apiGroup business
        @apiPermission registered user

        @apiDescription
        modified: change category type from string to number.<br/>
        modified: add name attribute.<br />
        modified: change deal type from string to number.<br/>
        todo validation<br/>
        query string <br />
        todo error / success return code in api <br />

        @apiParam {Number=0, 25, 50, 100} [itemsPerPage=25] items for each request.
        @apiParam {Number} [page=1] page you want to request from, start with 1.
        @apiParam {String="name", "description"} [orderBy=name] the items order by column you specified.
        @apiParam {String="true", "false"} [desc=false] the items order by descending or asceding order.


        @apiExample {curl} Example usage:
        curl -X GET -H "mTag: xx" -H "Content-Type:application/json" -i http://localhost/rest/customer/businesses?itemsPerPage=50&page=1&orderBy=name&desc=true

        {  
            "page":1,
            "type":"business",
            "orderBy":"name",
            "desc":0,
            "total":1,
            "itemsPerPage":25,
            "subtype":"list",
            "data":[  
                {  
                    "lat":120.678,
                    "id":1,
                    "deal":200,
                    "name":"Starbucks Coffee 31",
                    "image_url":"",
                    "long":23.5383,
                    "cat":1,
                    "description":"early Bird Special: Get  off."
                }
            ]
        }

        @apiSuccess {Number}   total         total items for pagination
        @apiSuccess {String}   orderBy       the items order by column you specified
        @apiSuccess {Number}   page          page you want to request from, start with 1
        @apiSuccess {Number}   itemsPerPage  items for each request
        @apiSuccess {String}   desc          the items order by descending or asceding order
        @apiSuccess {String}   type          request's type
        @apiSuccess {String}   subtype       request's subtype
        @apiSuccess {Object}   business       object of business.
        @apiSuccess {Number}   business.id    item's uniq id.
        @apiSuccess {String}   business.name  item's name.
        @apiSuccess {Number}   business.cat   item's business industry category.
        @apiSuccess {float}    business.lat   item's entered latitude.
        @apiSuccess {float}    business.long  item's entered longitude.
        @apiSuccess {String}   business.address item's address
        @apiSuccess {String}   business.description item's description.
        @apiSuccess {Number}   business.deal  item's deal.
        @apiSuccess {String}   business.image_url  items's image url.


        @apiError CE_INVALID_PARAM invalid parameter
        HTTP/1.0 400 BAD REQUEST
        {
            "errorId": 2001,
            "message": "{'pages'}"
        }
        """
        # check the request is validtion,
        # ex: we not allow request arg 'itemsPerPage1'

        validSet = set(field_inputs_wrap.keys())
        requestArgsSet = set(request.dataDictWrap.keys())

        if not ExtraParamsIsValid(requestArgsSet, validSet):
            return omitError(
                ErrorMsg=repr(requestArgsSet.difference(validSet))), 400

        # one to many
        # 1. parsing reqest
        try:
            for k, v in field_inputs.items():
                field_inputs[k]['required'] = False

            orgArgs, self.args = GetRequestArgs(
                None, field_inputs_wrap,
                dict((col, request.args.get(col)) for col in request.args))
            # get default value
            # print(self.args, 'self.args', resource_fields_wrap)
            self.response = dict(
                marshal(self.args, resource_fields_wrap).items())

            self.args[field_inputs_wrap_head] = []
        except Exception as error:
            logger.debug('traceback.format_exc(%s)', traceback.format_exc())

            return omitError(ErrorMsg=repr(error)), 400

        itemsPerPage = self.response['itemsPerPage']
        page = self.response['page']
        orderBy = getattr(obj, self.response['orderBy'])
        isDesc = getattr(orderBy, 'desc' if self.response['desc'] else 'asc')

        r = obj.query.filter(obj.isdel == False).order_by(isDesc())
        _r = r.all()
        self.args['total'] = len(_r)

        if itemsPerPage is not 0:
            _r = r.offset(itemsPerPage * (page-1))\
                    .limit(itemsPerPage)\
                    .all()

        r = _r
        # 2. export to user
        for _r in r:
            __r = dict(
                (col, getattr(_r, col)) for col in _r.__table__.columns.keys())
            #__r['description'] = getattr(_r.detail, 'description')

            # (1, 'icon'), (2, 'bg'), (3, 'gallery')
            ___r = pics.query.filter(pics.business_id == _r.id,
                                     pics.type == 1).scalar()
            __r['image_url'] = getattr(___r, 'path', "")
            self.args[field_inputs_wrap_head].append(__r)

        resource_fields_wrap[field_inputs_wrap_head] = fields.List(
            fields.Nested(resource_fields))
        self.args['type'] = "business"
        self.args['subtype'] = "list"
        return marshal(self.args, resource_fields_wrap), 200
Exemple #12
0
    def get(self, id):
        """Get all data, getall
        """
        """get pics by business id

        @api {get} /rest/pic/gallery/:id get pictures list with business id
        @apiVersion 0.0.5
        @apiName ListPicsUnderBusiness
        @apiGroup business
        @apiPermission registered user


        @apiDescription
        todo certificate with cookies / oauth 2.0<br />
        todo long/lat validation<br />
        todo metadata for counter of registerd devices<br />
        todo error / success return code in api

        @apiParam {Number} id business id
        @apiExample {curl} Example usage:
        curl -X GET -H "mTag: xx" -H "Content-Type:application/json" http://localhost/rest/pic/gallery/1
        {  
            "orderBy":"id",
            "itemsPerPage":25,
            "subtype":"gallery",
            "desc":0,
            "data":[  
                {  
                    "path":"/img/customer/1/BYTPH2_20160618_6615.jpg",
                    "id":5,
                    "width":1024,
                    "height":1365
                },
                {  
                    "path":"/img/customer/1/ZS0LII_10473.jpg",
                    "id":6,
                    "width":1024,
                    "height":1365
                },
                {  
                    "path":"/img/customer/1/G30SLL_20160618_6615.jpg",
                    "id":9,
                    "width":1024,
                    "height":1365
                }
            ],
            "type":"pic",
            "total":3,
            "page":1
        }

        @apiSuccess {Number}   total         total items in one business 
        @apiSuccess {String}   orderBy       the items order by column you specified
        @apiSuccess {Number}   page          page you want to request from, start with 1
        @apiSuccess {Number}   itemsPerPage  items for each request
        @apiSuccess {String}   type          request's type
        @apiSuccess {String}   subtype       request's subtype

        @apiSuccess {Object[]}   data       object

        @apiSuccess {Number}     data.id    image's id
        @apiSuccess {Number}     data.path  image's url that you could directly access
        @apiSuccess {Number}     data.height image's height(px)
        @apiSuccess {Number}     data.width image's width(px)
        """

        # check the request is validtion,
        # ex: we not allow request arg 'itemsPerPage1'

        validSet = set(field_inputs_wrap.keys())
        requestArgsSet = set(request.dataDictWrap.keys())

        if not ExtraParamsIsValid(requestArgsSet, validSet):
            return omitError(
                ErrorMsg=repr(requestArgsSet.difference(validSet))), 400

        # one to many
        # 1. parsing reqest
        try:
            for k, v in field_inputs.items():
                field_inputs[k]['required'] = False

            orgArgs, self.args = GetRequestArgs(
                None, field_inputs_wrap,
                dict((col, request.args.get(col)) for col in request.args))
            # get default value
            # print(self.args, 'self.args', resource_fields_wrap)
            self.response = dict(
                marshal(self.args, resource_fields_wrap).items())

            self.args[__heads__] = []
        except Exception as error:
            logger.debug('traceback.format_exc(%s)', traceback.format_exc())

            #return omitError(ErrorMsg=repr(error)), 400
            return omitError('CE_INVALID_PARAM', 'not found'), 400

        itemsPerPage = self.response['itemsPerPage']
        page = self.response['page']
        orderBy = getattr(obj, self.response['orderBy'])
        isDesc = getattr(orderBy, 'desc' if self.response['desc'] else 'asc')

        # FIXME: use mapping table
        r = obj.query.filter(obj.type == 3, obj.business_id == id,
                             obj.isdel == False).order_by(isDesc())
        _r = r.all()
        self.args['total'] = len(_r)

        if itemsPerPage is not 0:
            _r = r.offset(itemsPerPage * (page-1))\
                    .limit(itemsPerPage)\
                    .all()

        r = _r
        # 2. export to user
        self.args[field_inputs_wrap_head] = []
        for _r in r:
            __r = dict(
                (col, getattr(_r, col)) for col in _r.__table__.columns.keys())

            # FIXME: use mapping table
            if __r['type'] == 3:
                rest_pic_prefix = os.path.join(REST_PIC_PREFIX, 'customer',
                                               str(__r['business_id']))
                __r['path'] = os.path.join(rest_pic_prefix, __r['path'])
                self.args[field_inputs_wrap_head].append(__r)

        _resource_fields_wrap = resource_fields_wrap.copy()
        _resource_fields_wrap.pop('gallery_nr', None)
        _resource_fields_wrap[field_inputs_wrap_head] = fields.List(
            fields.Nested(resource_fields_post))

        self.args['type'] = "pic"
        self.args['subtype'] = "gallery"

        return marshal(self.args, _resource_fields_wrap), 200
Exemple #13
0
    def get(self, id):
        """get all devices info by business id

        @api {get} /rest/pushno/reg/:id registed devices under business id
        @apiVersion 0.0.4
        @apiName GetAllDeviceByBusinessId
        @apiGroup pushno
        @apiPermission registered user

        @apiParam {Number} id business id, you can get from GetAllCustomerBusinesses.

        @apiDescription
        todo certificate with cookies / oauth 2.0<br />
        todo long/lat validation<br />
        todo metadata for counter of registerd devices<br />
        todo error / success return code in api

        @apiExample {curl} Example usage:

        curl -X GET -H "mTag: xx" -H "Content-Type:application/json" http://localhost/rest/pushno/reg/1

        {  
            "orderBy":"user_id",
            "desc":0,
            "subtype":"reg",
            "itemsPerPage":25,
            "page":1,
            "data":[  
                {  
                    "dev_id":"eh2AM5l18K8:APA91bFsjAU_FmdkdTeErJ_BRSiz7_Iipi_r12QTscHciTVJmj1gcSK_p9l6BfgYtudntv0Ht7JNiyCe8lS-WdrL8zHOwCdGFdRutEDglPV1I9EeROVbhwVX0rcd_PS_jdCTQZ22inFq",
                    "id":4,
                    "user_id":1,
                    "business_id":1,
                    "type":1
                },
                {  
                    "dev_id":"eh2AM5l18K8:APA91bFsjAU_FmdkdTeErJ_BRSiz7_Iipi_r12QTscHciTVJmj1gcSK_p9l6BfgYtudntv0Ht7JNiyCe8lS-WdrL8zHOwCdGFdRutEDglPV1I9EeROVbhwVX0rcd_PS_jdCTQZ22inFq",
                    "id":5,
                    "user_id":1,
                    "business_id":1,
                    "type":1
                },
                {  
                    "dev_id":"eh2AM5l18K8:APA91bFsjAU_FmdkdTeErJ_BRSiz7_Iipi_r12QTscHciTVJmj1gcSK_p9l6BfgYtudntv0Ht7JNiyCe8lS-WdrL8zHOwCdGFdRutEDglPV1I9EeROVbhwVX0rcd_PS_jdCTQZ22inFq",
                    "id":6,
                    "user_id":1,
                    "business_id":1,
                    "type":1
                }
            ],
            "total":3,
            "type":"pushno"
        }

        @apiSuccess {Number}   total         total items for pagination
        @apiSuccess {String}   orderBy       the items order by column you specified
        @apiSuccess {Number}   page          page you want to request from, start with 1
        @apiSuccess {Number}   itemsPerPage  items for each request
        @apiSuccess {String}   desc          the items order by descending or asceding order
        @apiSuccess {String}   type          request's type

        @apiSuccess {Object[]}   devices       object of devices
        @apiSuccess {Number}     devices.id    device's uniq id
        @apiSuccess {Number}     devices.user_id registered user id
        @apiSuccess {Number=1, 2}devices.type    device's type, 1 for andriod, 2 for ios
        @apiSuccess {String{..254}}   devices.dev_id  device's id
        """

        # check the request is validtion,
        # ex: we not allow request arg 'itemsPerPage1'

        validSet = set(field_inputs_wrap.keys())
        requestArgsSet = set(request.dataDictWrap.keys())

        if not ExtraParamsIsValid(requestArgsSet, validSet):
            return omitError(
                ErrorMsg=repr(requestArgsSet.difference(validSet))), 400

        # one to many
        # 1. parsing reqest
        try:
            for k, v in field_inputs.items():
                field_inputs[k]['required'] = False

            orgArgs, self.args = GetRequestArgs(
                None, field_inputs_wrap,
                dict((col, request.args.get(col)) for col in request.args))
            # get default value
            # print(self.args, 'self.args', resource_fields_wrap)
            self.response = dict(
                marshal(self.args, resource_fields_wrap).items())

            self.args[field_inputs_wrap_head] = []
        except Exception as error:
            logger.debug('traceback.format_exc(%s)', traceback.format_exc())

            return omitError(ErrorMsg=repr(error)), 400

        itemsPerPage = self.response['itemsPerPage']
        page = self.response['page']
        orderBy = getattr(obj, self.response['orderBy'])
        isDesc = getattr(orderBy, 'desc' if self.response['desc'] else 'asc')

        r = obj.query.filter(obj.business_id == id,
                             obj.isdel == False).order_by(isDesc())
        _r = r.all()
        self.args['total'] = len(_r)

        if itemsPerPage is not 0:
            _r = r.offset(itemsPerPage * (page-1))\
                    .limit(itemsPerPage)\
                    .all()

        r = _r
        # 2. export to user
        for _r in r:
            __r = dict(
                (col, getattr(_r, col)) for col in _r.__table__.columns.keys())
            self.args[field_inputs_wrap_head].append(__r)

        _resource_fields = resource_fields.copy()
        _resource_fields_wrap = resource_fields_wrap.copy()
        _resource_fields_wrap[field_inputs_wrap_head] = fields.List(
            fields.Nested(_resource_fields))
        self.args['type'] = "pushno"
        self.args['subtype'] = "reg"
        return marshal(self.args, _resource_fields_wrap), 200
Exemple #14
0
    def post(self):
        try:
            self.dataDict = request.get_json()
            request.dataDict = self.dataDict[__head__]
            add_argument(_reqparse, field_inputs)
            args = _reqparse.parse_args()
        except Exception as error:
            logger.debug('traceback.format_exc(%s)', traceback.format_exc())

            if error == type(BadRequest):
                return omitError(ErrorMsg='maybe json format error'), 400

            return omitError(ErrorMsg='{}'.format(error.args)), 400

        if db.session.query(obj.id).count() > limit['max']:
            return omitError('CE_EXCEED_LIMIT',
                             'limit is {}'.format(limit['max'])), 400

        try:
            # now we only support IPv4/IPv6
            args['addr1'] = inputs.is_ipv4_ipv6(args['addr1'],
                                                argument=args['ipVersion'])
        except socket.error as error:
            # Not legal
            logger.debug('traceback.format_exc(%s)', traceback.format_exc())
            return omitError(
                'CE_INVALID_PARAM',
                '`{}/{}`: {}'.format(args['addr1'], args['ipVersion'],
                                     error.args)), 400

        ip = args['addr1']
        ver = args['ipVersion']
        pre = args['addr2']

        try:
            if args['type'] == 'Single':
                # TODO: maybe we limit that could not pass anything in attribute 'addr2'
                pass

            elif args['type'] == 'Range':
                # do the same as below
                pre = inputs.is_ipv4_ipv6(pre, argument=ver)
                # legal
            elif args['type'] == 'Subnet':
                # do the same as below
                if 'IPv4' == ver:
                    #NOTICE: maybe correct user's input?
                    try:
                        ip = inputs.is_cidr(ip, argument=pre)
                    except Exception as error:
                        pre = inputs.is_netmask(pre)

                elif 'IPv6' == ver:
                    pre = inputs.is_ipv6_prefix(ip, argument=pre)
                # legal

        except Exception as error:
            # Not legal
            logger.debug('traceback.format_exc(%s)', traceback.format_exc())
            return omitError('CE_INVALID_PARAM', '`{}/{}({})`: {}'.\
                    format(ip, pre, ver, error.args)), 400

        r = obj()
        for k, v in args.items():
            if v != None:
                setattr(r, k, v)

        db.session.add(r)

        try:
            db.session.flush()
            db.session.commit()
        except Exception as error:
            db.session.rollback()
            logger.warning('session commit error(%s)', error)

            if exc.IntegrityError == type(error):
                return omitError('CE_NAME_CONFLICT', repr(error)), 400

            return omitError(ErrorMsg=repr(error)), 400

        # get id immediately after call commit
        for col in r.__table__.columns.keys():
            args[col] = getattr(r, col)

        args[__head__] = args
        _resource_fields = {}
        _resource_fields[__head__] = fields.Nested(resource_fields)
        return marshal(args, _resource_fields), 200
Exemple #15
0
}
field_inputs_detail_rates['avatar_url'] = {
    'validator': validate.str_range(argument={
        'low': 1,
        'high': 255
    }),
    'type': fields.String()
}
field_inputs_detail['deals'] = {
    # type attribute for marshal
    'type': {
        fields.List(
            fields.Nested({
                'title': {
                    'type': fields.String(attribute='title')
                },
                'description': {
                    'type': fields.String(attribute='description')
                },
            }))
    },
    # validate attribute for reqparse
    'validator': {
        fields.List(
            fields.Nested({
                'title': {
                    'type': validate.str_range(argument={
                        'low': 1,
                        'high': 64
                    })
                },
                'description': {
Exemple #16
0
    def get(self):
        """Get all data, getall

        @api {get} /rest/customer/comments list all comments
        @apiName GetAllCustomerComments
        @apiVersion 0.0.5
        @apiGroup campaign
        @apiPermission registered user


        @apiDescription
        todo validation<br/>
        todo query target<br/>

        @apiParam {Number=0, 25, 50, 100} [itemsPerPage=25] items for each request.
        @apiParam {Number} [page=1] page you want to request from, start with 1.
        @apiParam {String} [orderBy=mtime] the items order by column you specified.
        @apiParam {String="true", "false"} [desc=false] the items order by descending or asceding order.
        @apiParam {String={..254}} [q] query string for pre-defined columns.


        @apiExample {curl} Example usage:
        curl -X GET -H "mTag: xx" -H "Content-Type:application/json" http://localhost/rest/customer/comments

        HTTP/1.0 200 OK
        {  
            "page":1,
            "orderBy":"mtime",
            "desc":0,
            "total":2,
            "subtype":"comment",
            "type":"business",
            "itemsPerPage":25,
            "data":[  
                {  
                    "id":1,
                    "business_id":1,
                    "mtime":"2016-08-31 00:14:56.215613",
                    "content":"Starbucks were all over Singapore and the quality ",
                    "rate":2,
                    "user":{  
                        "id":2,
                        "avatar_url":""
                    }
                },
                {  
                    "id":2,
                    "business_id":1,
                    "mtime":"2016-08-31 04:23:15.682219",
                    "content":"Starbucks were all over Singapore and the quality ",
                    "rate":2,
                    "user":{  
                        "id":2,
                        "avatar_url":""
                    }
                }
            ]
        }

        @apiSuccess {Number}   total         total items for pagination.
        @apiSuccess {String}   orderBy       the items order by column you specified.
        @apiSuccess {Number}   page          page you want to request from, start with 1.
        @apiSuccess {Number}   itemsPerPage  items for each request.
        @apiSuccess {String}   desc          the items order by descending or asceding order.

        @apiSuccess {Object[]} data       List of business's comments.
        @apiSuccess {Number}   data.id    item's uniq id.
        @apiSuccess {String}   data.content  item's comment content
        @apiSuccess {Number}   data.rate   item's rate for business item
        @apiSuccess {Number}   data.mtime  items's latest modified time with ISO 8601 format
        @apiSuccess {Object}   data.user   item's author infomation
        @apiSuccess {Number}   data.user.id  item's author id
        @apiSuccess {String}   data.user.avatar_url  item's author avatar

        @apiError CE_INVALID_PARAM invalid parameter
        HTTP/1.0 400 BAD REQUEST
        {
            "errorId": 2001,
            "message": "{'pages'}"
        }

        @apiError CE_NOT_EXIST item not found
        HTTP/1.0 400 BAD REQUEST
        {
            "errorId": 2003,
            "message": "id 1 not found"
        }
        """
        # check the request is validtion,
        # ex: we not allow request arg 'itemsPerPage1'

        validSet = set(field_inputs_wrap.keys())
        requestArgsSet = set(request.dataDictWrap.keys())

        if not ExtraParamsIsValid(requestArgsSet, validSet):
            return omitError(
                ErrorMsg=repr(requestArgsSet.difference(validSet))), 400

        # one to many
        # 1. parsing reqest
        try:
            for k, v in field_inputs.items():
                field_inputs[k]['required'] = False

            orgArgs, self.args = GetRequestArgs(
                None, field_inputs_wrap,
                dict((col, request.args.get(col)) for col in request.args))
            # get default value
            # print(self.args, 'self.args', resource_fields_wrap)
            self.response = dict(
                marshal(self.args, resource_fields_wrap).items())

            self.args[field_inputs_wrap_head] = []
        except Exception as error:
            logger.debug('traceback.format_exc(%s)', traceback.format_exc())

            return omitError(ErrorMsg=repr(error)), 400

        itemsPerPage = self.response['itemsPerPage']
        page = self.response['page']
        orderBy = getattr(obj, self.response['orderBy'])
        isDesc = getattr(orderBy, 'desc' if self.response['desc'] else 'asc')

        r = obj.query.filter(obj.isdel == False).order_by(isDesc())
        _r = r.all()
        self.args['total'] = len(_r)

        if itemsPerPage is not 0:
            _r = r.offset(itemsPerPage * (page-1))\
                    .limit(itemsPerPage)\
                    .all()

        r = _r
        # 2. export to user
        for _r in r:
            __r = dict(
                (col, getattr(_r, col)) for col in _r.__table__.columns.keys())
            ___r = db.session.query(Users).\
                    filter(_r.user_id == Users.id).scalar()
            __r['user'] = {'id': ___r.id, 'avatar_url': ___r.avatar_url}
            ___r = db.session.query(rates).\
                    filter(_r.user_id == rates.user_id, _r.business_id == rates.business_id).scalar()
            if ___r is not None:
                __r['rate'] = ___r.rate

            self.args[field_inputs_wrap_head].append(__r)

        _resource_fields = resource_fields.copy()
        _resource_fields_wrap = resource_fields_wrap.copy()
        _resource_fields['user'] = fields.Nested(resource_fields_user)
        _resource_fields_wrap[field_inputs_wrap_head] = fields.List(
            fields.Nested(_resource_fields))
        self.args['type'] = "business"
        self.args['subtype'] = "comment"
        return marshal(self.args, _resource_fields_wrap), 200
Exemple #17
0
    def get(self, id):
        """get one item

        @api {get} /rest/customer/business/:id get one business
        @apiName GetCustomerBusiness
        @apiVersion 0.0.4
        @apiGroup customer
        @apiPermission registered user

        @apiDescription
        todo validation<br />
        todo query target<br/>

        @apiParam {Number} id business id, you can get from GetAllCustomerBusinesses.

        @apiExample Example usage:
        HTTP/1.0 200 OK
        {
            "id": 1,
            "name": "Starbucks Coffee",
            "image_url": "/business/1/icon",
            "cat": 1,
            "deal": 200,
            "lat": 120.678469,
            "long": 23.538302,
            "description": "Early Bird Special: Get $2 off.",
            "detail": {
                "rate": 4.3,
                "rates": [
                    {"u_id": 1, "avatar_url": "/user/1/avater"},
                    {"u_id": 2, "avatar_url": "/user/2/avater"}
                ],
                "deals": [
                    {"title": "morning", "description": "for every one"}
                ],
                "open": "0600",
                "close": "2100",
                "dist": 12333333,
                "address": "CA",
                "images_url": {
                    "bg": "/business/1/bg",
                    "icon": "/business/1/icon"
                }
            }
        }



        @apiSuccess {Object}     business       object of business.
        @apiSuccess {Number}     business.id    item's uniq id.
        @apiSuccess {String}     business.name  item's name.
        @apiSuccess {Number}     business.cat   item's business industry category.
        @apiSuccess {float}      business.lat   item's entered latitude.
        @apiSuccess {float}      business.long  item's entered longitude.
        @apiSuccess {String}     business.address item's address
        @apiSuccess {String}     business.description item's description.
        @apiSuccess {Number}     business.deal  item's deal.
        @apiSuccess {String}     business.image_url  items's image url.
        @apiSuccess {Object}     business.detail item's detail
        @apiSuccess {Float}      business.detail.rate item's rate, average from each comments
        @apiSuccess {Object[]}   business.detail.rates item's brief comments 
        @apiSuccess {Number}     business.detail.rates.u_id comment's author id
        @apiSuccess {String}     business.detail.rates.avatar_url comment's author avatar url path
        @apiSuccess {Object[]}   business.detail.deals item's deals
        @apiSuccess {String}     business.detail.deals.title item's deal title
        @apiSuccess {String}     business.detail.deals.description item's deal description
        @apiSuccess {String}     business.detail.open item open time with 24h format
        @apiSuccess {String}     business.detail.open item close time with 24h format
        @apiSuccess {Number}     business.detail.dist item's distance farward with your current location, the unit is meter
        @apiSuccess {Object}     business.detail.images_url item images' path
        @apiSuccess {String}     business.detail.images_url.bg item backgound images' path
        @apiSuccess {String}     business.detail.images_url.icon item icon images' path



        @apiError CE_INVALID_PARAM invalid parameter
        HTTP/1.0 400 BAD REQUEST
        {
           "errorId": 2001,
           "message": "{'pages'}"
        }

        @apiError CE_NOT_EXIST item not found
        HTTP/1.0 400 BAD REQUEST
        {
            "errorId": 2003,
            "message": "id 17 not found"
        }

        """
        requestArgsSet = set((col) for col in request.args)
        if not ExtraParamsIsValid(requestArgsSet):
            return omitError(ErrorMsg=repr(set(
                (col) for col in request.args))), 400

        r = detail.query.filter(detail.business_id == id,
                                detail.isdel == False).scalar()

        if r is None:
            return omitError('CE_NOT_EXIST', 'id {} not found'.format(id)), 400

        self.args = {}
        self.args[field_inputs_wrap_head] = {}
        #self.args[field_inputs_wrap_head][__head_detail__] = {}
        _resource_fields_wrap = resource_fields_wrap.copy()
        for col in resource_fields_wrap:
            if col not in ['type', 'subtype']:
                _resource_fields_wrap.pop(col, None)
        #_resource_fields_detail_wrap = {}
        #resource_fields_detail[__head_detail_rates__] = \
        #       fields.List(fields.Nested(resource_fields_detail_rates))
        resource_fields_detail[__head_detail_deals__] = \
               fields.List(fields.Nested(resource_fields_detail_deals))

        _resource_fields_detail_rates = {}
        #_resource_fields_detail_rates['user'] = fields.Nested(resource_fields_detail_rates)
        _resource_fields_detail_rates = resource_fields_detail_rates.copy()
        resource_fields_detail['users'] = \
               fields.List(fields.Nested(_resource_fields_detail_rates))
        #resource_fields.update(resource_fields_detail)
        resource_fields_detail[__head_detail_images_url__] = \
                fields.Nested(resource_fields_detail_images_url)
        #resource_fields[__head_detail__] = fields.Nested(_resource_fields_detail_wrap)
        #_resource_fields_wrap[field_inputs_wrap_head] = fields.Nested(resource_fields)
        _resource_fields_wrap[field_inputs_wrap_head] = fields.Nested(
            resource_fields_detail)

        #print('_resource_fields_wrap ', resource_fields)

        _r = r
        #for col in resource_fields.keys():
        #    self.args[field_inputs_wrap_head][col] = getattr(_r, col)
        #for col in resource_fields.keys():
        for col in _r.__table__.columns.keys():
            self.args[field_inputs_wrap_head][col] = getattr(_r, col)

        self.args[field_inputs_wrap_head]['name'] = getattr(_r.meta, 'name')

        rate = 0
        self.args[field_inputs_wrap_head]['rate'] = rate
        self.args[field_inputs_wrap_head]['users'] = []
        self.args[field_inputs_wrap_head][__head_detail_deals__] = []
        self.args[field_inputs_wrap_head]['images_url'] = {}


        __r = db.session.query(rates).\
                filter(rates.business_id == id).all()
        r_len = len(__r)
        self.args[field_inputs_wrap_head]['rate_nr'] = r_len
        if r_len > 0:
            for ___r in __r:
                rate += ___r.rate
            self.args[field_inputs_wrap_head]['rate'] = int(rate / r_len)

        # FIXME: hard code
        __r = db.session.query(comment).\
                filter(comment.business_id == id).order_by(comment.mtime.desc()).offset(0).limit(5).all()
        r_len = len(__r)
        self.args[field_inputs_wrap_head]['user_nr'] = r_len
        if r_len > 0:
            for __r in __r:
                ___r = db.session.query(Users).\
                        filter(__r.user_id == Users.id).scalar()

                self.args[field_inputs_wrap_head]['users'].append(
                    #{'user':
                    {
                        'id': ___r.id,
                        'avatar_url': ___r.avatar_url
                    }
                    #}
                )

        # TODO: get favorite by User id from session

        _r = deals.query.filter(deals.business_id == id).all()
        r_len = len(_r)
        if r_len:
            for __r in _r:
                self.args[field_inputs_wrap_head][
                    __head_detail_deals__].append({
                        'title':
                        __r.title,
                        'description':
                        __r.description
                    })

        _r = pics.query.filter(pics.business_id == id).all()
        # (1, 'icon'), (2, 'bg'), (3, 'gallery')
        r_len = len(_r)
        if r_len > 0:
            # TODO: mapping table
            for __r in _r:
                if getattr(__r, 'type') == 1:
                    self.args[field_inputs_wrap_head]['images_url']['icon'] = \
                    getattr(__r, 'path')
                    r_len -= 1
                elif getattr(__r, 'type') == 2:
                    self.args[field_inputs_wrap_head]['images_url']['bg'] = \
                    getattr(__r, 'path')
                    r_len -= 1

        self.args[field_inputs_wrap_head]['gallery_nr'] = r_len
        self.args[field_inputs_wrap_head]['id'] = id

        self.args['type'] = "business"
        self.args['subtype'] = "overview"
        #print('self.args= ', self.args, '_resource_fields_wrap', _resource_fields_wrap)

        return marshal(self.args, _resource_fields_wrap), 200
Exemple #18
0
    def get(self):
        """Get all data, getall
        """
        # check the request is validtion,
        # ex: we not allow request arg 'itemsPerPage1'

        validSet = set(field_inputs_wrap.keys())
        requestArgsSet = set(request.dataDictWrap.keys())

        if not ExtraParamsIsValid(requestArgsSet, validSet):
            return omitError(
                ErrorMsg=repr(requestArgsSet.difference(validSet))), 400

        # one to many
        # 1. parsing reqest
        try:
            for k, v in field_inputs.items():
                field_inputs[k]['required'] = False

            orgArgs, self.args = GetRequestArgs(
                None, field_inputs_wrap,
                dict((col, request.args.get(col)) for col in request.args))
            # get default value
            # print(self.args, 'self.args', resource_fields_wrap)
            self.response = dict(
                marshal(self.args, resource_fields_wrap).items())

            self.args[field_inputs_wrap_head] = []
        except Exception as error:
            logger.debug('traceback.format_exc(%s)', traceback.format_exc())

            return omitError(ErrorMsg=repr(error)), 400

        itemsPerPage = self.response['itemsPerPage']
        page = self.response['page']
        orderBy = getattr(obj, self.response['orderBy'])
        isDesc = getattr(orderBy, 'desc' if self.response['desc'] else 'asc')

        r = obj.query.filter(obj.isdel == False).order_by(isDesc())
        _r = r.all()
        self.args['total'] = len(_r)

        if itemsPerPage is not 0:
            _r = r.offset(itemsPerPage * (page-1))\
                    .limit(itemsPerPage)\
                    .all()

        r = _r
        # 2. export to user
        for _r in r:
            __r = dict(
                (col, getattr(_r, col)) for col in _r.__table__.columns.keys())
            self.args[field_inputs_wrap_head].append(__r)

        _resource_fields = resource_fields.copy()
        _resource_fields_wrap = resource_fields_wrap.copy()
        _resource_fields_wrap[field_inputs_wrap_head] = fields.List(
            fields.Nested(_resource_fields))
        self.args['type'] = "business"
        self.args['subtype'] = "rate"
        return marshal(self.args, _resource_fields_wrap), 200
Exemple #19
0
    def post(self):
        """upload pics to business

        @api {post} /rest/pic/gallery upload multiple pictures to business
        @apiVersion 0.0.5
        @apiName UploadPicsToBusiness
        @apiGroup business
        @apiPermission registered user


        @apiDescription
        todo certificate with cookies / oauth 2.0<br />
        todo long/lat validation<br />
        todo metadata for counter of registerd devices<br />
        todo error / success return code in api

        @apiHeader {String}         file[]      upload file path 
        @apiHeader {Number}         business_id upload to business
        @apiHeader {String={customer}}         type      upload type
        @apiExample {curl} Example usage:
        curl -v -i -X POST -H "Content-Type: multipart/form-data" -F "file[]=@20160618_6615.jpg" -F "business_id=1" -F type="customer" -F "file[][email protected]" http://localhost/rest/pic/gallery

        {  
            "type":"pic",
            "data":[  
                {  
                    "id":9,
                    "path":"/img/customer/1/G30SLL_20160618_6615.jpg",
                    "height":1365,
                    "width":1024
                },
                {  
                    "id":10,
                    "path":"/img/customer/1/3AZGA4_10473.jpg",
                    "height":1365,
                    "width":1024
                }
            ],
            "page":1,
            "subtype":"gallery",
            "gallery_nr":2,
            "total":6
        }

        @apiSuccess {Number}   total         total items in one business 
        @apiSuccess {String}   orderBy       the items order by column you specified
        @apiSuccess {Number}   page          page you want to request from, start with 1
        @apiSuccess {Number}   gallery_nr    current upload files number
        @apiSuccess {String}   type          request's type
        @apiSuccess {String}   subtype       request's subtype

        @apiSuccess {Object[]}   data       object

        @apiSuccess {Number}     data.id    image's id
        @apiSuccess {Number}     data.path  image's url that you could directly access
        @apiSuccess {Number}     data.height image's height(px)
        @apiSuccess {Number}     data.width image's width(px)
        """

        try:
            orgArgs, self.args = GetTwoLayerRequestArgs(
                None, field_inputs, request.form)
        except Exception as error:
            logger.debug('traceback.format_exc(%s)', traceback.format_exc())

            return omitError('CE_INVALID_PARAM', 'not found'), 400

        id = self.args['business_id']
        type = self.args['type']
        #print(self.args, 'self.args', id, type)
        #self.args = {}
        #id = request.form.get('business_id')
        #type = request.form.get('type')

        #if type not in PIC_ALLOWED_TYPE:
        #    logger.debug('%s not in PIC_ALLOWED_TYPE', type)
        #    type = None

        #if not id or not type:
        #    return omitError('CE_INVALID_PARAM', 'id {} not found'.format(id)), 400

        print("galleryed_files", request.files, "form data=", request.form)

        # 1. check id exist
        r = business.query.filter(business.id == id,
                                  business.isdel == False).scalar()

        if r is None:
            return omitError('CE_NOT_EXIST', 'id {} not found'.format(id)), 400

        # if dir not exist, create it
        # /img/business/1/
        pic_dir = os.path.join(STATIC_ROOT, PIC_PREFIX, type, str(id))
        rest_pic_prefix = os.path.join(REST_PIC_PREFIX, type, str(id))

        if not os.path.exists(pic_dir):
            os.makedirs(pic_dir)

        # TODO: review trigger time
        # 2. check last status that records are same with local
        _pics = []
        count = 0
        filenames = next(os.walk(pic_dir))[2]
        _filenames = filenames.copy()
        print("filenames=", _filenames)
        ps = obj.query.filter(obj.business_id == id).all()
        for v in ps:
            #print("filenames=", filenames, "v.path=", v.path)
            if v.path in filenames:
                count += 1
                _filenames.remove(v.path)
            else:
                # prepare remove
                _pics.append(v)

        # TODO: need check duplicate record?
        # 2.1. commit to delete not relationship records
        try:
            for v in _pics:
                db.session.delete(v)

            db.session.flush()
            db.session.commit()
        except Exception as error:
            db.session.rollback()
            logger.warning('session commit error(%s)', error)

            return omitError(ErrorMsg=repr(error)), 400

        # remove not exist db's file
        for v in _filenames:
            os.remove(os.path.join(pic_dir, v))

        # 3. validate follows spec
        if count > max:
            return omitError('CE_EXCEED_LIMIT', 'limit is {}'.format(max)), 400

        # 4. check pic name
        _pics = []
        filenames = []
        galleryed_files = request.files.getlist("file[]")
        print("galleryed_files file[]= ", galleryed_files)

        if len(galleryed_files) == 0:
            galleryed_files = request.files.getlist("customer")  # for ios
            print("galleryed_files customer= ", galleryed_files)

        for file in galleryed_files:
            # Check if the file is one of the allowed types/extensions
            if file and self.allowed_file(file.filename):
                # Make the filename safe, remove unsupported chars
                filename = secure_filename(file.filename)
                print("file.filename=", file.filename, "filename=", filename)
                # Move the file form the temporal folder to the gallery
                # folder we setup
                p = obj()
                rs = ''.join(
                    random.SystemRandom().choice(string.ascii_uppercase +
                                                 string.digits)
                    for _ in range(6))
                # 5FATMM_35e4183b.jpg.png -> 5FATMM_35e4183b.png
                extend = os.path.splitext(filename)[1]
                #print("self.remove_extend(filename)=", self.remove_extend(filename))
                p.path = '_'.join([rs, self.remove_extend(filename)]) + extend
                p.business_id = id
                # (1, 'icon'), (2, 'bg'), (3, 'gallery')
                p.type = 3

                _pics.append(p)
                filenames.append(filename)

        # 4. move to pic dir
        # FIXME: check file exist if abnormal error that db record save but pic not exist
        self.args[field_inputs_wrap_head] = []
        path = []
        _filenames = []
        for k, v in enumerate(_pics):
            filename = os.path.join(pic_dir, filenames[k])
            n_filename = os.path.join(pic_dir, v.path)

            try:
                # FIXME: handle <FileStorage: '35e4183b.jpg.png' ('application/octet-stream')>)
                galleryed_files[k].save(filename)
                #import shutil
                #shutil.copy(filename, n_filename)
                os.rename(filename, n_filename)
                _filenames.append(n_filename)

                print("n_filename = ", n_filename, "filename=", filename)
                img = Image.open(n_filename)
                s = img.size
                ratio = 0
                v.width = s[0]
                v.height = s[1]
                if s[0] > MAXWIDTH:
                    ratio = MAXWIDTH / s[0]
                    v.width = MAXWIDTH
                    v.height = int(round(s[1] * ratio))
                    img.thumbnail((v.width, v.height), Image.ANTIALIAS)
                print("img = ", img, "n_filenam=", n_filename, "format:",
                      img.format, "width:", MAXWIDTH, ", height: ",
                      int(round(s[1] * ratio)), "orgsize:", s)
                #img.save(n_filename, img.format)
                # FIXME: open 35e4183b.jpg.png error
                img.save(n_filename)

            except IOError:
                #for v in _filenames:
                #    os.remove(v)

                return omitError('CE_IMAGE_RESIZE',
                                 'image resize {} error'.format(
                                     filenames[k])), 400

        # 5. commit to save
        try:
            for v in _pics:
                db.session.add(v)

            db.session.flush()
            db.session.refresh(r)

            for v in _pics:
                _pic = dict((col, getattr(v, col))
                            for col in v.__table__.columns.keys())
                print("_pic:", _pic)
                _pic['path'] = os.path.join(rest_pic_prefix, v.path)
                self.args[field_inputs_wrap_head].append(_pic)

            db.session.commit()
        except Exception as error:
            db.session.rollback()
            logger.warning('session commit error(%s)', error)

            return omitError(ErrorMsg=repr(error)), 400

        #output = {"type": "pic", "subtype": "gallery",
        #        "imgs": {"total": count, "gallery_nr": len(_pics), "path": (path)}}

        for v in ['itemsPerPage', 'desc', 'orderBy']:
            resource_fields_wrap.pop(v, None)

        _resource_fields = {}
        resource_fields_wrap[field_inputs_wrap_head] = fields.List(
            fields.Nested(resource_fields_post))

        self.args['total'] = len(
            obj.query.filter(obj.business_id == id, obj.isdel == False).all())
        self.args['gallery_nr'] = len(_pics)
        self.args['type'] = "pic"
        self.args['subtype'] = "gallery"
        return marshal(self.args, resource_fields_wrap), 200