Set up Firebase to upload user files

If you’ve read my previous post on uploading files to server, you might have noticed that it was not an easy task to achieve.

There is way too much boilerplate code for uploading a single file, and it will be much more complex in case we plan to upload multiple files, which I need to do for my project.

So what’s the solution to this?

ENTER FIREBASE!

Yeah, you read it right, Firebase once again to the rescue!

I came to know that firebase allows user to store and access the files easily to the built in storage.

Enough chatter for now, lets get to code!

Step 1 :

Add your project to Firebase from the console.

newProj.PNG

Click on the Blue button

Step 2 :

Add Firebase to your webapp

Open the project, you’ve just created and click on the bright red button that says, “ Add Firebase to your web app”

addFirebase.PNGCopy the contents from here and paste it after your HTML code.

Step 3 :

Open the “Storage” tab from the navigation drawer and navigate to the rules tab over there.
We need to set up specific rules as to who all can upload and read files to the storage bucket.

storageRules.PNG
For testing purposes, I’ve allowed everyone to read and write to my storage, but that shouldn’t be the case for your production app

Step 4 :

Add code for uploading your files.

First create a document selection widget and an upload button in your website’s index.html.

<tr>
<td valign=”top”>
<label for=”icon”>Zip File</label>
</td>
<td valign=”top”>
<input accept=”.zip” type=”file” id=”uploadZip” name=”icon”>
</td>
</tr>

Next, create a button to initiate the upload

<tr>
<td colspan=”5″ style=”text-align:center”>
<button type=”submit”>Upload Zip</button>
</td>
</tr>

Next up, inside the JavaScript, add a submitlistener for the submit button and call preventDefault inside it to prevent the form from doing the default action.

var form = document.querySelector(“form”);
form.addEventListener(“submit”, function(event) {
event.preventDefault();

Next up, get a reference to the upload location from your firebase storage bucket.

var timestamp = Number(new Date());
var storageRef = firebase.storage().ref(timestamp.toString());

Next, get the upload button from its ID and add its contents to a variable named file_data.

var $ = jQuery;
var file_data = $(‘#uploadZip’).prop(‘files’)[0];

Now upload that file to firebase.

storageRef.put(file_data);

If everything went as expected, you’ll be able to see the uploaded files onto your firebase console.

 storage

So, you can really appreciate the awesomeness of Firebase by now.
It has replaced the work done by over 50+ lines of code (spread around AJAX calls, PHP Scripts and JavaScript methods) by a single method call.

I would urge you to go through the documentation for more clarity on this.
https://firebase.google.com/docs/storage/

Well, that was it for now.
Next time, I’ll tell you how to retrieve the files back from the storage and add user’s details to Firebase Database.(Yeah, no need for Tables and SQL anymore!)

Cheers. 😀

Uploading a file to a server via PHP

Uploading a file to a server via PHP

If you have been following my posts about my GSoC project, you would be knowing that we are making an app generator which will allow users to easily generate an android app for any event that they plan to host.

So, the next thing that we wanted in our app was to allow the users to upload a zip containing the json files (in case they don’t have an API, from where app can fetch data from) and then upload it to the server where we can use these files during the app compilation.

Steps below will tell you , how we achieved it :

Changes to HTML

First thing that we needed to do was add a file upload element to out HTML page that would allow only .zip files to be uploaded.
It was pretty simple one liner code which goes as follows

<tr>
<td valign=”top”>
<label for=”sessions”>Zip containing .json files</label>
</td>
<td valign=”top”>
<input accept=”.zip” type=”file” id=”uploadZip” name=”sessions”>
</td>
</tr>

PHP script to upload file on to the server

Next, we needed a server sided script (I used PHP) which would upload the zip provided by the user on to the server and store it to a unique location for each user.
The code for that was,

<?php
if ( 0 < $_FILES[‘file’][‘error’] ) {
echo ‘Error: ‘ . $_FILES[‘file’][‘error’] . ‘<br>’;
}
else {
move_uploaded_file($_FILES[‘file’][‘tmp_name’],“/var/www/html/uploads/upload.zip”);
}
?>

So what is happening here is basically the input arg. is first checked whether it is null or not null.
If it is null, and error is thrown back to the user, else the file is renamed and uploaded to the uploads folder in the server’s public directory.

Changes to the JavaScript

This was the part that needed most of the changes to be done, we first had to store the file that is to be uploaded in the form data, and then make and AJAX call to the php file located on the server.

var file_data = $(‘#uploadZip’).prop(‘files’)[0];
var form_data = new FormData();
form_data.append(‘file’, file_data);
$.ajax(
{ url: ‘/upload.php’, // point to server-side PHP script
cache: false,
contentType: false,
processData: false,
data: form_data,
type: ‘post’,
success: function(php_script_response){
ajaxCall1(); } //Chain up another AJAX call for further operations
});

So, that’s almost it!
Some server sided changes were also required like allowing the web user to execute the upload.php script and making the uploads directory writable by the web user.

Well, does it work?

Um, yeah it does.
There are a few issues with concurrent users which we are still debugging, but apart from that it works like a charm!

Here you can see a folder created by each user based on his/her timestamp
And here you can see the file that was uploaded y him/her
screenshot-area-2016-07-04-124957
Lastly our webapp (Looks stunning right?)

So, that was all for this week, hope to see you again next time.
Cheers and all the best 🙂

Error Handling in Retrofit 2

For the Open Event android app we were using retofit 1.9 with an okhttp stack plus a gson parser but recently retrofit 2.0 was released and it was a major update in the sense that it a lot of things have been changed.

For starters, you don’t have to declare synchronous and asynchronous requests upfront and you can just decide that while executing. The code for that will look something like this. This is how we define our request methods in our api service

import retrofit.Call;
public interface APIService {
   @POST(“/list”)
   Call<Repo> loadRepo();
}

Now if we want to make a synchronous request, we can make it like

Call<Repo> call = service.loadRepo();
Repo repo = call.execute();

and for an asynchronous request, we can call enqueue()

Call<Repo> call = service.loadRepo();
call.enqueue(new Callback<Repo>() {
    @Override
    public void onResponse(Response<Repo> response) {
    // Get result Repo from response.body()    
    }
    @Override
    public void onFailure(Throwable t) {

    }
});

And another thing that changed in the async call throws a throwable on failure, so essentially the RetrofitError class is gone and since we were using that in our app, we had to modify the whole error handling in the app, basically from the grounds up.

So, when we decided to move to retrofit 2 after the stable version was released, we had to change a lot of code and the main part that was affected was the error handling. So, replacing the retrofitError class, I used the throwable directly to retrieve the error type something like this

if (error.getThrowable() instanceof IOException) { 
    errorType = “Timeout”; 
    errorDesc = String.valueOf(error.getThrowable().getCause()); 
} 
else if (error.getThrowable() instanceof IllegalStateException) {                 
    errorType = “ConversionError”; 
    errorDesc = String.valueOf(error.getThrowable().getCause()); 
} else { 
    errorType = “Other Error”; 
    errorDesc = String.valueOf(error.getThrowable().getLocalizedMessage()); 
}

This was ofcourse for all failure events. And to handle all response events I compared the HTTP status codes and displayed the errors :

Integer statusCode = response.getStatusCode(); 
if (statusCode.equals(404)) { 
    // Show Errors in a dialog
    showErrorDialog(“HTTP Error”, statusCode + “Api Not Found”); 
}

This is how we can compare other HTTP errors in retrofit and assign the correct status accordingly. I personally think that this is a better implementation than Retrofit 1.9 and the RetrofitError was a bit tedious to work with. It wasn’t very thought of before implementation because it was not easy to tell what kind of error exactly occured. With Response codes, one can see what are the exact error one faces and can gracefully handle these errors.

Using TabLayouts in your Android app

So while making a sessions schedule for the open event app, I wanted to separate the sessions on the basis of the days they are scheduled for to improve the visual clarity. So to do this I had various approaches like add a filter to separate by date or add checkboxes to show only checked dates but I though they’d look ugly. Instead the best option was to add tabs in a fragment with a viewpager to scroll within them : It looks appealing, has simple and clean UI, easier to implement with the new design library. So, naturally I opted for using the Tablayout from the design Library.

Earlier, when the Support design library was not introduce, it was really a tedious job to add it to our app since we had to extend Listeners to check for tab changes and we had to manually open fragments when a tab was selected or unselected or even when it was reselected. Essentially this meant a lot of errors and memory leaks. In the design library we essentially need to add tablayout and a viewpager to our layout like this :

<android.support.design.widget.AppBarLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <android.support.design.widget.TabLayout
        android:id="@+id/tabLayout"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        app:tabGravity="fill"
        app:tabMode="fixed"
        app:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar" />

    <android.support.v4.view.ViewPager
        android:id="@+id/viewpager"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:background="@android:color/white" />

</android.support.design.widget.AppBarLayout>

Next in our activity/ fragment, we can just inflate this view and create an adapter for the viewpager extending a FragmentPagerAdapter:

public class OurAdapter extends FragmentPagerAdapter {
    private final List<Fragment> mFragmentList = new ArrayList<>();
    private final List<String> mFragmentTitleList = new ArrayList<>();

    public ScheduleViewPagerAdapter(FragmentManager manager) {
        super(manager);
    }

    @Override
    public Fragment getItem(int position) {
        return mFragmentList.get(position);
    }

    @Override
    public int getCount() {
        return mFragmentList.size();
    }

    public void addFragment(Fragment fragment, String title, int day) {

        mFragmentList.add(fragment);
        mFragmentTitleList.add(title);
    }

    @Override
    public CharSequence getPageTitle(int position) {
        return mFragmentTitleList.get(position);
    }
}

Now I had to make dynamic number of tabs, since I wanted the app to customisable on the number of days listed in the json downloaded from the server. So, I made some changes in the traditional code. This is what we do in our activity/fragment’s onCreate/OnCreatView :

viewPager = (ViewPager) view.findViewById(R.id.viewpager);

for (int i = 0; i < daysofEvent; i++) {
    adapter.addFragment(new DayScheduleFragment(),title, dayNo);
}

viewPager.setAdapter(adapter);
scheduleTabLayout = (TabLayout) view.findViewById(R.id.tabLayout);
scheduleTabLayout.setupWithViewPager(viewPager);

This is it. Now we have a basic working tablayout in a viewpager. This also has the capability to change according to the number of days specified in the json we have written.

Earlier without the design library, we would have to even add switch cases in the FragmentPagerAdapter like this :

public class OurAdapter extends FragmentPagerAdapter {
 
 public TabsPagerAdapter(FragmentManager fm) {
    super(fm);
 }
 
 @Override
 public Fragment getItem(int index) {
 
 switch (index) {
 case 0:
    return new FirstFragment();
 case 1:
    return new SecondFragment();
 case 2:
    return new ThirdFragment();
 }
 
 return null;
 }

Then we would have to override methods to listen to activities in tabs :

@Override
public void onTabReselected(Tab tab, FragmentTransaction ft) {
}

@Override
public void onTabSelected(Tab tab, FragmentTransaction ft) {
// on tab selected
// show respected fragment view
   viewPager.setCurrentItem(tab.getPosition());
}

@Override
public void onTabUnselected(Tab tab, FragmentTransaction ft) {
}

And more code to listen for swiping within tabs in a viewpager:

/**
* on swiping the viewpager make respective tab selected
**/
viewPager.setOnPageChangeListener(new ViewPager.OnPageChangeListener() {

@Override
public void onPageSelected(int position) {

// on changing the page
// make respected tab selected
actionBar.setSelectedNavigationItem(position);
}

@Override
public void onPageScrolled(int arg0, float arg1, int arg2) {
}

@Override
public void onPageScrollStateChanged(int arg0) {
}
});

You see how easy this got with the inclusion of TabLayout.

Now for the final product I made after inflating the fragments and adding recyclerviews for the schedule, I got this :

Swipable tabs

I urge you to try swipable tabs in your app as well. Adios till next time.

Getting Signed Release apk’s from the command line

 

View story at Medium.com

If anyone of you has deployed an application on the play store, you may have most probably used Android Studio’s built in Generate signed apkoption.

The generate apk option in android studio

Recently while making the Open Event Apk generator, I had to make release apk’s, so that they could be used by an event organiser to publish their app, plus apk’s had to be signed because if they were not signed, it would be impossible to upload due to checks by Google.

Error shown on the developers console

So since I was building the app using the terminal and I didn’t have the luxury of signing the app using Android studio and I had to look for alternatives. Luckily I found two of them :

  1. Using the Signing configs offered by gradle
  2. Using the Oracle sun jarsigner

First of all the signing configs in gradle is a great way to do this. Most Open source apps use this as a way to put their code out for everyone to view and sucessfully hide any private keys and password.

You just need to add few lines of code in your app level build.gradle file and create a file called keystore.properties

In your keystore.properties, we just need to store the sensitive info and this file will be accessible only to people who are part of the project.

storePassword=myStorePassword
keyPassword=mykeyPassword
keyAlias=myKeyAlias
storeFile=myStoreFileLocation

Next we go to the build.gradle and add these lines to read the keystore.properties file and it’s variables

// Create a variable called keystorePropertiesFile, and initialize it to your
// keystore.properties file, in the rootProject folder.
def keystorePropertiesFile = rootProject.file("keystore.properties")

// Initialize a new Properties() object called keystoreProperties.
def keystoreProperties = new Properties()

// Load your keystore.properties file into the keystoreProperties object.
keystoreProperties.load(new FileInputStream(keystorePropertiesFile))

Next we can add the signingConfigs task and reference the values we got above over there

android {
    signingConfigs {
        config {
            keyAlias keystoreProperties['keyAlias']
            keyPassword keystoreProperties['keyPassword']
            storeFile file(keystoreProperties['storeFile'])
            storePassword keystoreProperties['storePassword']
        }
    }
    ...
  }

So As you see this is as simple as this but according to my requirements this seemed a bit tedious since a person setting up the apk generator had to make a keystore file, then find the build.gradle and change the path of the keystore file according to the server directories. So this does the trick but this can be so tedious for someone with no technical experience, so I researched on other solutions and then I got it : Jarsigner and Zipalign

First of all,the jarsigner and zipalign are 2 great tools and the best part about them is that both of them work perfectly with a just one line commands. For signing the app :

jarsigner -keystore <keystore_file> -storepass <storepassword> <apknameTosigned> <alias>

and then zipaligning :

zipalign -v 4 <unaligned-apk-location> <path-to-generated-aligned-apk>

So this is it, we finally used these 2 commands to sign and zipalign an apk and it works perfectly fine. Please test and share comments of the demo live @ http://192.241.232.231. Ciao !

Next steps to an Open Event Android Applications

This year also I’ll be working on the FOSSASIA Open Event project for Google Summer of Code 2016. It’s an honour to be working with such an elite team of people. We have 10 people working on Open event this time : 6 on the server and 2 each on the client apps ( Android and Webapp)

So what are our plans for this year, let’s have a look :

The system was basically setup last year but when used it for FOSSASIA 2016, we got to know the bugs it had and it was these bugs that made it unusable. for instance, the server had lack of permissions which allowed anyone to come and change data on the server which is why instead of using the server, we went with a spreadsheet and made a parser to convert the spreadsheet data into json files. So we made this Scraper that we used to create json files and commit them to github repo. We used this json as Github Api and made a website here that displays a neat schedule.

For the android app, since the json was not of the original format we used while building the server, it was buggy because it didn’t show data at a lot of places and we saw the need for many other features like live sessions, notifications for changes in timings, broadcasts from the organisers etc. That is why we have Open Event this time again as a GSoC project and it’s bigger this time with 10 students and almost as much mentors. Justin is heading the mentors team this time along with Mario to guide us into making the system perfect.

On the Android side me and Harshit Dwivedi will be taking care of everything. Since I was at FOSSASIA 2016, I talked to a lot of attendees and got to know their feedback therefore I know what all we need to include and will work really hard to make the system a success.

Adios till the next post!

Community Building in India

Along with Arnav and Jigyasa we organised an event to promote contributions to open source projects. We especially wanted to get people interested in the projects we are working on this summer with FOSSASIA. So yeah, we had an awesome event planned in collaboration with the Organising committee of Esya’15 (My college’s Technical festival) and Women who code Delhi. Also, Another fellow working with the Python software Foundation Yash volunteered as speaker to share his experiences.

We had an awesome turnout of about 150 odd people. So Arnav started off with his presentation where he talked about his experience with Open source technologies and How he got into development. He talked about some important things like Why he likes FOSS, his contributions etc. which got the participants really excited. He also talked about some of his projects and GSoC. Then he moved on to our project and how’s it been like till now. You can find his slides here.

During Arnav’s presentation, Mario came online and just after Arnav was done, We put Mario on Live hangout’s video call with the participants. Mario talked about his experience with OSS and why he likes it. He also talked about some projects as well as answered questions that the attendees had. It was a very informative and inspiring talk. Thank you mario for that.

Then Jigyasa made her presentation. Right when she was in the middle of her presentation, his mentor Martin came online on hangouts and her presentation was cut short. It was pretty cool to have Martin as well. Though his children were playing in the background and making some noises😛 but the talk was pretty informative.

Next I put on the pre recorded video Mohit had sent me talking about his experience and some tips to start a beautiful journey into the open source world. His video very precise and to the point. I liked that about the video. The content was really good. Thank you Mohit to take out time to make the recording.

Lastly I gave my presentation where I talked about some myths regarding open source. Then I talked about my experience as a programmer and an Open source enthusiast. For the maximum part of my presentation, I talked about our GSoC project. Arnav also joined me during the time where I was showing some of our work. The participants also asked questions about our project during the allocated time. We also gave them the links to the repos and mailing list etc. to get them a starting point to contribute to FOSSASIA. It was a cool event all in all.

Wrapping up our first steps – Event Server, Material Design, Daily Scrum

The Event Organizer application has already the basic features and we can move to apply more advanced feature. But let explain me, what me and my friends have done recently.

Our application is already able to manage conferences and events. An owner can edit and change events in the way he/she wants to. And we have two version of this app for websites and for mobile phones(Android). The orga serv which I prepared share Json API to both Android and Web app. I guess it is really comfortable solution because it enables to share date between web and mobile app. Our app’s template style is based on material bootstrap, the same is used by Arnav in his application. It is very flat design.

Zrzut ekranu 2015-07-06 o 22.58.07
First Version of Open EVent Menu Bar

What I really like during this term is daily scrum, where we can share what we have already done, what are we going to do next, and what were the obstacles. Because of it, we can easily be in touch and avoid duplicating our work. We can also discuss and quickly choose the most useful solution. Duke and Mario accompany us and as always were ready to help with any trouble.

Arnav and Manan also organized a conference on their university. Many students were invited and discussed about taking part in open source projects. I regret not to having taken part in it, but India is so far from my country, that I could not get there.

I hope that the starting up part of this project will be also so developing and exciting, and we will finish it with a huge success. And all of us will be very proud, learn many new things, and improve our experience.

In the nearest future Arnav, Duke and me are going to create three environments: staging, production, and development. It helps us to organize our work. I am sure that we manage to do it.

Ok, so stay tuned. “Show must go on”! We don’t stop working! 😉

Using Material Design for the Open Event App

This week I had the chance to go into more depth on the material design principles and I must say that the design itself is awesome. So, I got  started building the user interface of our event app.

After looking at a lot of apps. I decided to make a recycler view list of cardviews. Cool right? Looks awesome too. I did this by put an imageview, relative layout and a linear layout in a linear layout. In the second linear layout I added the textviews for the position, organization. Finally the description textview was added in the relative layout. This is how I designed the card layout. Now for the recycler view of cardviews, I added cardview layout to the recycler view adapter to make the list of cardviews.

I also wrote unit tests for the database this week as suggested by Mohit. At first, they were failing and since I didn’t have any experience writing tests for databases, I wasn’t able to debug them. So, I took help from mohit who ended up identifying the problems which was arising due to the singleton in the database. Apparently, You can’t use singletons in a test because we don’t control the creation of the singleton object, as it is performed inside a static method. There is no way to mock the object in order to test the behavior of our method in isolation. So for now mohit has used dependency injection to make the tests work but I am working on a way to remove the injection.

This is pretty much all from this week. Adios !!

Basic UI implementation for Event app

I am enjoying this a lot. It has been a wonderful experience till now working with all my team members and my mentors. I mean I am learning something new everyday. Like I have learned squashing git commits using rebasing and pushing, which I am using a lot now. I am also following a code review policy suggested by mohit where I push to a new branch on my fork and then create a PR, after which mohit reviews my code and then merges it. This is a very nice practice and I think that every open source developer should follow such practices to get the best quality code out there.

Moving on, this week I was mainly working on implementing the UI for the app. For this I studied layouts of various apps and came out with what I though was best. So I though I should implement the Tracks Fragment First where I add all the tracks I have updated inserted into the database in a recycler view. I take up a very basic layout for now just showing the track name and description.

Screenshot_2015-06-12-20-53-13

I also added the sponsor fragment where I have used Picasso by Square Inc. to download the Logo images and displayed them in a recycler View. Here also I researched various options to download the Sponsor Logo images and I come up with one clear winner : Picasso. We can resize image, load from URL’s,drawables etc. all in just one line of code.

I also added the speaker fragment in which I used a bit complex layout as I had to get the speaker image, name, designation and description all in one recycle view ViewHolder. So after some hiccups I managed to get it right. I used Picasso here as well for the speaker Image. Although I still have to add further details to this fragment and the others. I’ll do so in this week. I am planning on adding some material design with some clickables for different holders. I have also started to work on a list of cardviews as well.

Screenshot_2015-06-12-20-53-28