Categories
discuss

Parsing a YAML document with a map at the root using snakeYaml

I want to read a YAML document to a map of custom objects (instead of maps, which snakeYaml does by default). So this:

19:
  typeID: 2
  limit: 300
20:
  typeID: 8
  limit: 100

Would be loaded to a map which looks like this:

Map<Integer, Item>

where Item is:

class Item {
    private Integer typeId;
    private Integer limit;
}

I could not find a way to do this with snakeYaml, and I couldn’t find a better library for the task either.

The documentation only has examples with maps/collections nested inside other objects, so that you can do the following:

    TypeDescription typeDescription = new TypeDescription(ClassContainingAMap.class);
    typeDescription.putMapPropertyType("propertyNameOfNestedMap", Integer.class, Item.class);
    Constructor constructor = new Constructor(typeDescription);
    Yaml yaml = new Yaml(constructor);
    /* creating an input stream (is) */
    ClassContainingAMap obj = (ClassContainingAMap) yaml.load(is);

But how do I go about defining the Map format when it is at the root of the document?

Answer

You need to add a custom Constructor. However, in your case you don’t want register an “item” or “item-list” tag.

In effect, you want to apply Duck Typing to your Yaml. It’s not super efficient, but there is a relatively easy way to do this.

class YamlConstructor extends Constructor {
  @Override
  protected Object constructObject(Node node) {

    if (node.getTag() == Tag.MAP) {
        LinkedHashMap<String, Object> map = (LinkedHashMap<String, Object>) super
                .constructObject(node);
        // If the map has the typeId and limit attributes
        // return a new Item object using the values from the map
        ...
    }
     // In all other cases, use the default constructObject.
    return super.constructObject(node);
Categories
discuss

How to detect whether android app is running UI test with Espresso

I am writing some Espresso tests for Android. I am running in the the following problem:

In order for a certain test case to run properly, I need to disable some features in the app. Therefore, in my app, I need to detect whether I am running Espresso test so that I can disable it. However, I don’t want to use BuildConfig.DEBUG to because I don’t want those features to be disabled in a debug build. Also, I would like to avoid creating a new buildConfig to avoid too many build variants to be created (we already have a lot of flavors defined).

I was looking for a way to define buildConfigField for test but I couldn’t find any reference on Google.

Answer

Combined with CommonsWare’s comment. Here is my solution:

I defined an AtomicBoolean variable and a function to check whether it’s running test:

private AtomicBoolean isRunningTest;

public synchronized boolean isRunningTest () {
    if (null == isRunningTest) {
        boolean istest;

        try {
            Class.forName ("myApp.package.name.test.class.name");
            istest = true;
        } catch (ClassNotFoundException e) {
            istest = false;
        }

        isRunningTest = new AtomicBoolean (istest);
    }

    return isRunningTest.get ();
}

This avoids doing the try-catch check every time you need to check the value and it only runs the check the first time you call this function.

Categories
discuss

Router.use() requires middleware function but got a undefined

I am trying to set up my node server / REST api.

For this i have a few different files:

division_model.js:

    module.exports = function(express, sequelize)
{
    var router = express.Router();
    router.route('/division');
    var DataTypes = require("sequelize");



    var Division = sequelize.define('division', {
            id: DataTypes.INTEGER,
            organization_id: DataTypes.INTEGER,
            location_id: DataTypes.INTEGER,
            name: DataTypes.STRING,
            parent_id: DataTypes.INTEGER

        }, {    freezeTableName: true,
            instanceMethods: {
                retrieveAll: function (onSuccess, onError) {
                    Division.findAll({}, {raw: true})
                        .ok(onSuccess).error(onError);
                },
                retrieveById: function (user_id, onSuccess, onError) {
                    Division.find({where: {id: user_id}}, {raw: true})
                        .success(onSuccess).error(onError);
                },
                add: function (onSuccess, onError) {
                    var username = this.username;
                    var password = this.password;

                    var shasum = crypto.createHash('sha1');
                    shasum.update(password);
                    password = shasum.digest('hex');

                    Division.build({username: username, password: password})
                        .save().ok(onSuccess).error(onError);
                },
                updateById: function (user_id, onSuccess, onError) {
                    var id = user_id;
                    var username = this.username;
                    var password = this.password;

                    var shasum = crypto.createHash('sha1');
                    shasum.update(password);
                    password = shasum.digest('hex');

                    Division.update({username: username, password: password}, {where: {id: id}})
                        .success(onSuccess).error(onError);
                },
                removeById: function (user_id, onSuccess, onError) {
                    Division.destroy({where: {id: user_id}}).success(onSuccess).error(onError);
                }
            }
        }
    );

// on routes that end in /users/:user_id
// ----------------------------------------------------
    router.route('/division/:division_id')

// update a user (accessed at PUT http://localhost:8080/api/users/:user_id)
        .put(function (req, res) {
            var user = User.build();

            Division.username = req.body.username;
            Division.password = req.body.password;

            Division.updateById(req.params.division_id, function (success) {
                console.log(success);
                if (success) {
                    res.json({message: 'User updated!'});
                } else {
                    res.send(401, "User not found");
                }
            }, function (error) {
                res.send("User not found");
            });
        })

// get a user by id(accessed at GET http://localhost:8080/api/users/:user_id)
        .get(function (req, res) {
            var Division = Division.build();

            Division.retrieveById(req.params.division_id, function (users) {
                if (users) {
                    res.json(users);
                } else {
                    res.status(401).send("User not found");
                }
            }, function (error) {
                res.send("User not found");
            });
        })

// delete a user by id (accessed at DELETE http://localhost:8080/api/users/:user_id)
        .delete(function (req, res) {
            var division = Division.build();

            division.removeById(req.params.division_id, function (users) {
                if (users) {
                    res.json({message: 'User removed!'});
                } else {
                    res.status(401).send("User not found");
                }
            }, function (error) {
                res.send("User not found");
            });
        });
};

And my server.js

    // BASE SETUP
// =============================================================================
var express = require('express'),
    bodyParser = require('body-parser');
var app = express();
var router = express.Router();
var es = require('express-sequelize');
// =============================================================================

// IMPORT MODELS
// =============================================================================
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({
    extended: true
}));
var env = app.get('env') == 'development' ? 'dev' : app.get('env');
var port = process.env.PORT || 8080;

var Sequelize = require('sequelize');

// db config
var env = "dev";
var config = require('./database.json')[env];
var password = config.password ? config.password : null;

// initialize database connection
var sequelize = new Sequelize(
    config.database,
    config.user,
    config.password,
    {
        logging: console.log,
        define: {
            timestamps: false
        }
    }
);
//================================================================================

var division_model = require('./Divisions/division_model')(express,sequelize, router);

app.use('/division', division_model);

// REGISTER ROUTES
// =============================================================================
app.use('/api', app.router);

// START THE SERVER
// =============================================================================
app.listen(port);
console.log('Magic happens on port ' + port);

However with this i get the following error message when starting the server:

          throw new TypeError('Router.use() requires middleware function but got a
            ^
TypeError: Router.use() requires middleware function but got a undefined
    at Function.<anonymous> (/var/www/example/backend/node_modules/express/lib/router/index.js:446:13)
    at Array.forEach (native)
    at Function.use (/var/www/example/backend/node_modules/express/lib/router/index.js:444:13)
    at EventEmitter.<anonymous> (/var/www/example/backend/node_modules/express/lib/application.js:187:21)
    at Array.forEach (native)
    at EventEmitter.use (/var/www/example/backend/node_modules/express/lib/application.js:184:7)
    at Object.<anonymous> (/var/www/example/backend/server.js:42:5)
    at Module._compile (module.js:456:26)
    at Object.Module._extensions..js (module.js:474:10)
    at Module.load (module.js:356:32)

Can anyone tell me why this is happening?

Answer

You must return a router in your middleware here:

app.use('/division', division_model);

So, your module export function should end with:

return router;

You also have conflicting ideas when setting this up. If you want the app to define the route as /division which you do here:

app.use('/division', division_model);

then you do not need to redefine the route again like you do here:

var router = express.Router();
router.route('/division');

You can simply:

app.use(division_model);

— or —

/**
 * division_model.js
 */
var router = express.Router();
router.route('/');
//omitting route code
router.route('/:division_id');
//omitting route code

return router;

/**
 * server.js
 */

app.use('/division', division_model);
Categories
discuss

Login Example in Android using POST method using REST API

I am working on my First Android application where we have our own REST API, url will be like. “www.abc.com/abc/def/” . For login activity i need to do httppost by passing 3 parameters as identifier, email and password. Then after getting the http response, i need to show the dialogbox whether Invalid Credentials or Switch to another activity.

Can someone please show me sample code for how to do this?

Answer

An easy way to complete this task is to using a library, if your familiar with libraries. I recommend Ion because it’s small and easy to work with. Add the library and add the following snippet to the method of your choice.

Ion.with(getApplicationContext())
.load("http://www.example.com/abc/def/")
.setBodyParameter("identifier", "foo")
.setBodyParameter("email", "foo@foo.com")
.setBodyParameter("password", "p@ssw0rd")
.asString()
.setCallback(new FutureCallback<String>() {
   @Override
    public void onCompleted(Exception e, String result) {
        // Result
    }
});

Notice! If you want to make network calls you must add the following permission to your AndroidManifest.xml outside the <application> tag if you’re not aware of that.

<uses-permission android:name="android.permission.INTERNET" />

To check the response for successful login, or failure you can add the following snippet inside the onComplete-method (where the // Result is).:

    try {
        JSONObject json = new JSONObject(result);    // Converts the string "result" to a JSONObject
        String json_result = json.getString("result"); // Get the string "result" inside the Json-object
        if (json_result.equalsIgnoreCase("ok")){ // Checks if the "result"-string is equals to "ok"
            // Result is "OK"
            int customer_id = json.getInt("customer_id"); // Get the int customer_id
            String customer_email = json.getString("customer_email"); // I don't need to explain this one, right?
        } else {
            // Result is NOT "OK"
            String error = json.getString("error");
            Toast.makeText(getApplicationContext(), error, Toast.LENGTH_LONG).show(); // This will show the user what went wrong with a toast
            Intent to_main = new Intent(getApplicationContext(), MainActivity.class); // New intent to MainActivity
            startActivity(to_main); // Starts MainActivity
            finish(); // Add this to prevent the user to go back to this activity when pressing the back button after we've opened MainActivity
        }
    } catch (JSONException e){
        // This method will run if something goes wrong with the json, like a typo to the json-key or a broken JSON.
        Log.e(TAG, e.getMessage());
        Toast.makeText(getApplicationContext(), "Please check your internet connection.", Toast.LENGTH_LONG).show();
    }

Why do we need a try & catch, well first of all we are forced to and on the other hand, it will prevent the application to crash if something goes wrong with the JSON-parsing.

Categories
discuss

How to code using android studio to send an email

I’m planning to develop an android mobile application using android studio, where an user give email address and secret code. Then that secret code should be send to mentioned email address. Can any body share any code snippet in order to do this?

Answer

If you want to send email in background refer here

If user is waiting on screen use below method:

protected void sendEmail() {
      Log.i("Send email", "");

      String[] TO = {"someone@gmail.com"};
      String[] CC = {"xyz@gmail.com"};
      Intent emailIntent = new Intent(Intent.ACTION_SEND);
      emailIntent.setData(Uri.parse("mailto:"));
      emailIntent.setType("text/plain");


      emailIntent.putExtra(Intent.EXTRA_EMAIL, TO);
      emailIntent.putExtra(Intent.EXTRA_CC, CC);
      emailIntent.putExtra(Intent.EXTRA_SUBJECT, "Your subject");
      emailIntent.putExtra(Intent.EXTRA_TEXT, "Email message goes here");

      try {
         startActivity(Intent.createChooser(emailIntent, "Send mail..."));
         finish();
         Log.i("Finished sending email...", "");
      } catch (android.content.ActivityNotFoundException ex) {
         Toast.makeText(MainActivity.this, 
         "There is no email client installed.", Toast.LENGTH_SHORT).show();
      }
   }
Source: stackoverflow
Text is available under the Creative Commons Attribution-ShareAlike License; additional terms may apply. By using this site, you agree to the Privacy Policy, and Copyright Policy. Content is available under CC BY-SA 3.0 unless otherwise noted. The answers/resolutions are collected from stackoverflow, are licensed under cc by-sa 2.5 , cc by-sa 3.0 and cc by-sa 4.0 © No Copyrights, All Questions are retrived from public domain..