Implementing MVC on Engelsystem

Engelsystem is an MVC based PHP application, but there was a 4th ties, Pages, introduced with the traditional MVC pattern. It seems to have everything an event manager could want.

The Model-View-Control (MVC) pattern, originally formulated in the late 1970s, is a software architecture pattern built on the basis of keeping the presentation of data separate from the methods that interact with the data. In theory, a well-developed MVC system should allow a front-end developer and a back-end developer to work on the same system without interfering, sharing, or editing files either party is working on.

Like everything else in software engineering, it seems, the concept of Model-View-Controller was originally invented bySmalltalk programmers. More specifically, it was invented by one Smalltalk programmer, Trygve Reenskaug. Trygve maintains a page that explains the history of MVC in his own words.

Block Diagram for MVC
                                                                  Block Diagram for MVC

 

The components of an MVC pattern are explained as follows:

  1. MODEL: The Model is the name given to the permanent storage of the data used in the overall design.
    Models represent knowledge. A model could be a single object (rather uninteresting), or it could be some structure of objects.
  2. VIEW: The View is where data, requested from the Model, is viewed and its final output is determined. A view is a (visual) representation of its model. It would ordinarily highlight certain attributes of the model and suppress others. It is thus acting as a presentation filter.
    Traditionally in web apps built using MVC, the View is the part of the system where the HTML is generated and displayed. The View also ignites reactions from the user, who then goes on to interact with the Controller.
  3. CONTROLLER: The final component of the triad is the Controller.A controller is the link between a user and the system. It provides the user with input by arranging for relevant views to present themselves in appropriate places on the screen.
    Its job is to handle data that the user inputs or submits, and update the Model accordingly. The Controller’s life blood is the user; without user interactions, the Controller has no purpose.

 

Even though MVC was originally designed for personal computing, it has been adapted and is widely being used by web developers due to its emphasis on separation of concerns, and thus indirectly, reusable code. The pattern encourages the development of modular systems, allowing developers to quickly update, add, or even remove functionality.

layercake

 

Initially, in Engelsystem there were files distributed in 4 tiers, Model, View, Controller, Pages, which are mentioned as follows:

Pages:

admin_active.php
admin_arrive.php
admin_export.php
admin_free.php
admin_groups.php
admin_import.php
admin_log.php
admin_news.php
admin_questions.php
admin_rooms.php
admin_settings.php
admin_shifts.php
admin_user.php
guest_credits.php
guest_login.php
guest_start.php
guest_stats.php
user_atom.php
user_ical.php
user_messages.php
user_myshifts.php
user_news.php
user_questions.php
user_settings.php
user_shifts.php

Model:

AngelType_model.php
LogEntries_model.php
Message_model.php
NeededAngelTypes_model.php
Room_model.php
Settings_model.php
ShiftEntry_model.php
ShiftTypes_model.php
Shifts_model.php
UserAngelTypes_model.php
UserDriverLicenses.model.php
User_model.php

Controller

angeltype_controller.php
rooms_controller.php
shifts_controller.php
shifttypes_controller.php
user_angeltypes_controller.php
user_driver_licenses_controller.php
user_controller.php

View

AngelTypes_view.php
Questions_view.php
Rooms_view.php
ShiftEntry_view.php
ShiftTypes_view.php
Shifts_view.php
UserAngelTypes_view.php
UserDriverLicenses_view.php
User_view.php

 

There were 26 Pages files, in which there were both sql queries along with the controller code. All these files were refactured into Controller and Model(which contains sql queries) files seperately to implement proper MVC pattern in Engelsystem.

 

We are developing new feature for Engelsystem and we will be applying this WordPress like update system toEngelsystem in the upcoming weeks. Developers who are interested in contributing can work with us.

Development: https://github.com/fossasia/engelsystem             Issues/Bugs:https://github.com/fossasia/engelsystem/issues

Continue ReadingImplementing MVC on Engelsystem

Unit testing JSON files in assets folder of Android App

So here is the scenario, your android app has a lot of json files in the assets folder that are used to load some data when in first runs.
You are writing some unit tests, and want to make sure the integrity of the data in the assets/*.json are preserved.

You’d assume, that reading JSON files should not involve using the Android Runtime in any way, and we should be able to read JSON files in local JVM as well. But you’re wrong. The JSONObject and JSONArray classes of Android are part of android.jar, and hence

 
JSONObject myJson = new JSONObject(someString);

The above code will not work when running unit tests on local JVM.

Fortunately, our codebase already using Google’s GSoN library to parse JSON, and that works on local JVM too (because GSoN is a core Java library, not specifically an Android library).

Now the second problem that comes is that when running unit tests on local JVM we do not have the getResources() or getAssets() functions.
So how do we retrieve a file from the assets folder ?

So what I found out (after a bit of trial and error and poking around with various dir paths), is that the tests are run from the app folder (app being the Android application module – it is named app by default by Android Studio, though you might have had named it differently)

So in the tests file you can define at the beginning

    public static final String  ASSET_BASE_PATH = "../app/src/main/assets/";

And also create the following helper function

    public String readJsonFile (String filename) throws IOException {
        BufferedReader br = new BufferedReader(new InputStreamReader(new FileInputStream(ASSET_BASE_PATH + filename)));
        StringBuilder sb = new StringBuilder();
        String line = br.readLine();
        while (line != null) {
            sb.append(line);
            line = br.readLine();
        }

        return sb.toString();
    }

Now wherever you need this JSON data you can just do the following

        Gson gson = new GsonBuilder().create();
        events = gson.fromJson(readJsonFile("events.json"),
                Event.EventList.class);
        eventDatesList = gson.fromJson(readJsonFile("eventDates.json"), EventDates.EventDatesList.class);
Continue ReadingUnit testing JSON files in assets folder of Android App

Autocomplete Address Form using Google Map API

Google map is one of the most widely used API of Google as most of the websites use Google map for showing address location. For a static address it’s pretty simple. All you need to do is mention the address and the map will show the nearest location. Problem arrives when the address is dynamically putted by the user. Suppose for an event in event organizer server, one enters the location. The main component used while taking input location is Google Autocomplete. But we went a step further and parsed the entire address based on city, state, country, etc. and allowed user to input the details as well which gave them the nearest location marked in Map if autocomplete couldn’t find the address.

Autocomplete Location

Screenshot from 2016-07-27 06:52:37

As we can see, in the above input box we get suggestions by Google Map on entering first few letters of our address. To this, we need the API https://maps.googleapis.com/maps/api/js?key=YOUR_API_KEY&libraries=places&callback=initMap. You can find an example code of how to do this here.

After this is done, what we wanted is not to just include this address, but to provide a form to fill up the entire address in case some parts were missing on this address. The function that the autocomplete listens to is “place_changed” . So once we click on one of the options, this event is triggered. Once the event is triggered, we use the autocomplete.getPlace() to get the complete address json. The json looks something like this:

Screenshot from 2016-07-27 07:04:49

Now what we do is we create a form with input fields having the id same as the ones we require(e.g., country, administrative_area_level_1, locality, etc.). After that we select the long_name or the short_name from this json and put the value in the corresponding input field with the ids. The code for the process after getting the json is elaborated here.

Editing Address Form

After doing this it looks something like this:
Screenshot from 2016-07-27 07:12:13

However, now the important part is to show the map according to this fields. Also, every time we update a field, the map should be updated. For this we use a hack. Instead of removing the initial location field completely, we hide the field but keep the binding to autocomplete intact. As a result the map is shown when we select a particular address.

Now when we update the fields in the address form, we append the value of this field to the value in the initial location field. Though the field is hidden but it is still bound to autocomplete. As a result as soon as we append something to the string contained in the field, the map gets updated. Also, the updated value gets stored to the DB. Thus, with every update in field, the pointer is moved to the nearest location formed by appending all the data from the form.

After saving the location data to DB, if we wish to edit it, we can get back the json by making the same request with the location value. And then we will get back the same address form and the map accordingly.

Finally it looks something like this:

Screenshot from 2016-07-27 07:19:56

Continue ReadingAutocomplete Address Form using Google Map API

Testing Hero – II

I continued last weeks work on improving the testing framework and adding more test cases. While writing the test cases for create I had to write a separate test case for each kind of object. This caused a lot of repetition of code. Thus the first aim for the week was to design a mechanism to write generalized test cases so that we can have an array of object and loop through them and pass each object to the same test case.

https://github.com/societyserver/sTeam/issues/113

https://github.com/societyserver/sTeam/pull/114

Right now the structure has a central script called test.pike which imports various other scripts containing the test cases. Let us take one of these scripts, suppose move.pike. Now I wanted to write a generalized test case which performs the same action on various objects. So I created one more file containing this generalized test case and imported this into one of the testcases in move.pike. This test case in move.pike is responsible for enumerating the various kinds of objects, sending them to the generalized test case, collect the output and then send the result for the entire test to the central test.pike. Then I went ahead and implemented this model for moving various objects to non existential location and for creating various kinds of objects and the model seemed to work fairly well.

The journey was not so smooth. I had a few troubles on the way. In all the test cases I was deleting any objects that were created and used in the test. To delete any object I need to get a reference to the object. This reference keeps getting dropped for some reason and I get an error for calling the delete function on NULL as the reference no longer exists. I tried finding the cause of this and solve this bug, however I couldn’t and found a work around the errors by using if statements to check that the object references are not null before calling functions on these object references. I continued my work on generalizing the test cases and wrote the general tests for all the test cases in the move and create test suites.

In the later part of the week I started working on some merging with my team mate Ajinkya Wavare. I designed more test cases for checking the creation of groups and users. Groups could be created using the generalized test case however for users I had to add a special test case as the process of creating a user is different from creating other objects. I ended my week by writing the test case for a long standing error, i.e, call to the get_environment function.

testing hero 2
output of test
Continue ReadingTesting Hero – II

Using Cron Scheduling to automatically run background jobs

Cron scheduling is nothing new. It is basically a concept in which the system keeps executing lines of code every few seconds, minutes, or hours. It is required in many large applications which require some automation in their working. I had to use it for two purposes in our Open-Event application.

  • To automatically delete the items in the trash after a period of 30 days.
  • To automatically send after event mails to the speakers and organizers when an event gets completed

1. Delete items in Trash system

So the deleted items get stored in the trash of the admin. However if the items are not deleted or no action is performed on them then they should be deleted automatically if they stay in the trash for more than 30 days. I have used a framework – apscheduler (Advanced Python Scheduler) for this.The code is like this

from apscheduler.schedulers.background import BackgroundScheduler

def empty_trash():
 with app.app_context():
 print 'HELLO'
 events = Event.query.filter_by(in_trash=True)
 users = User.query.filter_by(in_trash=True)
 sessions = Session.query.filter_by(in_trash=True)
 for event in events:
 if datetime.now() - event.trash_date >= timedelta(days=30):
 DataManager.delete_event(event.id)

 for user in users:
 if datetime.now() - user.trash_date >= timedelta(days=30):
 transaction = transaction_class(Event)
 transaction.query.filter_by(user_id=user.id).delete()
 delete_from_db(user, "User deleted permanently")

 for session in sessions:
 if datetime.now() - session.trash_date >= timedelta(days=30):
 delete_from_db(session, "Session deleted permanently")


trash_sched = BackgroundScheduler(timezone=utc)
trash_sched.add_job(empty_trash, 'cron', day_of_week='mon-fri', hour=5,
                    minute=30)
trash_sched.start()

The trash_sched is initialized first. It is given an instance of BackgroundScheduler() meaning it will always run in the background as long as the application server is running.

The second line defines the trigger which is given to the scheduler meaning at what time intervals do we want the scheduler to execute the function.

trash_sched.add_job(empty_trash, 'cron', day_of_week='mon-fri', hour=5, 
                    minute=30)

Here the scheduler adds the function to the job list. The function is empty_trash and the trigger given here is ‘cron’. The following line:

day_of_week='mon-fri', hour=5, minute=30

sets the time at which the sheduler executes the job. The above line means that the job will be executed every day from Monday to Friday at 5:30 AM. Now coming to the function which is to be executed:

def empty_trash():
    with app.app_context():
        events = Event.query.filter_by(in_trash=True)
        users = User.query.filter_by(in_trash=True)
        sessions = Session.query.filter_by(in_trash=True)
        for event in events:
            if datetime.now() - event.trash_date >= timedelta(days=30):
                DataManager.delete_event(event.id)

        for user in users:
            if datetime.now() - user.trash_date >= timedelta(days=30):
                transaction = transaction_class(Event)
                transaction.query.filter_by(user_id=user.id).delete()
                delete_from_db(user, "User deleted permanently")

        for session in sessions:
            if datetime.now() - session.trash_date >= timedelta(days=30):
                delete_from_db(session, "Session deleted permanently")

There are three items in the trash: events, users and sessions. We get all the items in the trash by the query.all() method. Each model: Events, Users and Sessions has a column

trash_date = db.Column(db.DateTime)

The date on which the item is moved to the trash is stored in the trash_date column. And the following line:

 if datetime.now() - event.trash_date >= timedelta(days=30)

checks if the item has been in the trash for more than 30 days. If yes then it is deleted automatically. This function is constantly executed by the apscheduler according to the time settings given by us. Thus we do not need to manually delete the trash after 30 days.

2. Send After Event Mails

This is similar to the trash emptying function.

from apscheduler.schedulers.background import BackgroundScheduler

def send_after_event_mail():
 with app.app_context():
 events = Event.query.all()
 for event in events:
 upcoming_events = DataGetter.get_upcoming_events(event.id)
 organizers = DataGetter.get_user_event_roles_by_role_name(event.id, 'organizer')
 speakers = DataGetter.get_user_event_roles_by_role_name(event.id, 'speaker')
 if datetime.now() > event.end_time:
 for speaker in speakers:
 send_after_event(speaker.user.email, event.id, upcoming_events)
 for organizer in organizers:
 send_after_event(organizer.user.email, event.id, upcoming_events)

#logging.basicConfig()
sched = BackgroundScheduler(timezone=utc)
sched.add_job(send_after_event_mail, 'cron', day_of_week='mon-fri', hour=5, minute=30)
#sched.start()

The scheduler settings are the same as the trash scheduler settings. The function returns all the events and checks whether the event’s end_date has come or not. This check is performed against the present date by the following line:

if datetime.now() > event.end_time

If yes then the speakers and organizers for that event are obtained and after event mails are sent to them automatically.

In this way the whole system is automated. 🙂

Continue ReadingUsing Cron Scheduling to automatically run background jobs

Creating Dynamic Footer with Popover

  • Post author:
  • Post category:FOSSASIA

In Open-Event Webapp generator, the track page height varies according to the popover that appears on hovering the tracks. The problem with this design was the footer of the page that always remains static and produce a bad UI to user.

12

So, I have decided to make footer dynamic so that it varies it’s position according to the popover appeared on hover. The approach was a bit tricky but the diagram below will make it easy to understand.

Dynamic footer

The following code will work on hovering the track.

//popover.js 

var outerContheight= $('.main').offset().top + $('.main').outerHeight();
var tracknext= $(track).next();
var tracktocheck= track.offset().top + track.outerHeight() + 
 tracknext.outerHeight() + 15;
 var shift= tracktocheck - outerContheight;
 if(shift > 0){
 
 $('.footer').css({
 'position':'absolute',
 'top': outerContheight + shift,
 'width':'100%',
 'z-index': '999'
 })
 }

If shift > 0 which is calculated as shown in the above code it means that the footer needs to be shifted and hence we shift the footer by setting absolute position in CSS. Else we set position: static for footer.

 $('.footer').css({
 'position':'static'
 })

After following the above approach the footer position changes according to the popover. Here is the screencast for the approach.

 

Continue ReadingCreating Dynamic Footer with Popover

Unit Testing

There are many stories about unit testing. Developers sometimes say that they don’t write tests because they write a good quality code. Does it make sense, if no one is infallible?.

At studies only a  few teachers talk about unit testing, but they only show basic examples of unit testing. They require to write a few tests to finish final project, but nobody really  teaches us the importance of unit testing.

I have also always wondered what benefits can it bring. As time is a really important factor in our work it often happens that we simply resign of this part of process development to get “more time” rather than spend time on writing stupid tests. But now I know that it is a vicious circle.

Customers requierments does not help us. They put a high pressure to see visible results not a few statistics about coverage status. None of them cares about some strange numbers. So, as I mentioned above, we usually focuses on building new features and get riid of tests. It may seem to save time, but it doesn’t.

In reality tests save us a lot of time because we can identify and fix bugs very quickly. If a bug ocurrs because someone’s change we don’t have to spend long hours trying to figure out wgat is going out. That’s why we need tests.  

It is especially visible in huge open source projects. FOSSASIA organization has about 200 contributors. In OpenEvent project we have about 20 active developers, who generate many lines of code every single day. Many of them change over and over again as well as interfere  with each other.

Let me provide you with a simple example. In our team we have about 7 pull requests per day. As I mentioned above we want to make our code high quality and free of bugs, but without testing identifying if pull request causes a bug is very difficult task. But fortunately this boring job makes Travis CI for us. It is a great tool which uses our tests and runs them on every PR  to check if bugs occur. It helps us to quickly notice bugs and maintain our project very well.

What is unit testing?

Unit testing is a software development method in which the smallest testable parts of an application are tested

Why do we need writing unit tests?

Let me point all arguments why unit testing is really important while developing a project.

  • To prove that our code works properly

If developer adds another condition, test checks if method returns correct results. You simply don’t need to wonder if something is wrong with you code.

  • To reduce amount of bugs

It let you to know what inputs params’ function should get and what results should be returned. You simply don’t  write unused code

  • To save development time

Developers don’t waste time on checking every code’s change if his code works correctly

  • Unit tests help to understand software design
  • To provide quick feedback about method which you are testing
  • To help document a code

How to write unit test in Python

In my work I write use tests in Python. I am going to share my sample code  with you now

  • Import module unittest
  • Choose function to test
  • Write unit test

Example OpenEvent test in Python

class TestPagesUrls(OpenEventTestCase):

   def setUp(self):

       self.app = Setup.create_app()

   def test_if_urls_exist(self):

       """Test all urls via GET method"""

       with app.test_request_context():

           for rule in app.url_map.iter_rules():

               if excluded_paths(rule):

                   status_code = self.app.get(request.url[:-1] + str(rule).replace('//', '/'),        follow_redirects=True).status_code

                   self.assertTrue(status_code in [200, 302, 401])

 

I want to check if all views exist but it required a lot of time. That’s why I wonder I how to avoid writing similar tests. Finally, based  on our list of routes I am able to write test which checks code’s status  on every page.

If some of them response returns status_code different than 200, 302 or 401, test fails.This results means that somethings is wrong. Simple, isn’t it ?  Try to test it manually…. This one short test cover about 40 use cases…

This example shows an incredible value of unit tests! If developer makes a bug in response he receives an error that something is wrong with a view. Travis CI allows to reject all  wrong pull requests and merge only these which fulfill our quality requirements.   

Fixing  error is one part but finding a bug is even harder task. But an ability to detect bug on early stage of process development reduces cost of software.

 

Continue ReadingUnit Testing

Working with GCM Task Service on Android

The GCM Network Manager enables apps to register services that perform network-oriented tasks.
The API helps with scheduling these tasks, allowing Google Play services to batch network operations across the system.

Hence, multiple tasks get executed in a go, rather than executing each of them individually.
This in turns save battery as the mobile radio is awoken only once rather than waking up the device multiple times.

Using GCM Network Manager in our app

Add the dependency to build.gradle

dependencies {
    ...
    compile 'com.google.android.gms:play-services-gcm:8.4.0'
    ...
}

Next, declare a new Service in the Android Manifest which will make the network calls:

<service android:name=".GCMService"
        android:permission="com.google.android.gms.permission.BIND_NETWORK_TASK_SERVICE"
        android:exported="true">
   <intent-filter>
       <action android:name="com.google.android.gms.gcm.ACTION_TASK_READY"/>
   </intent-filter>
</service>

The name of the service (GCMService) is the name of the class that will extend GcmTaskService, which is the core class for dealing with GCM Network Manager. This service will handle the running of a task.

Next we will define the GCMSerice class

public class GCMService extends GcmTaskService {
        ...
}

On implementing the methods from GcmTaskService, we have something like this :

@Override
public int onRunTask(TaskParams taskParams) {
        switch (taskParams.getTag()) {
                case TAG_TASK_ONEOFF_LOG:
                        //bundle with other tasks and then execute
                        return GcmNetworkManager.RESULT_SUCCESS;
                case TAG_TASK_PERIODIC_LOG:
                        //run this periodically 
                        return GcmNetworkManager.RESULT_SUCCESS;
                default:
                        return GcmNetworkManager.RESULT_FAILURE;
        }
}

Once this is set up, we need to schedule tasks from our Activity.

This can be done easily by first creating an object of GcmNetworkManager and class and hook up tasks to be executed from the above defined service

private GcmNetworkManager mGcmNetworkManager;

@Override
protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        ...
        gcmNetworkManager = GcmNetworkManager.getInstance(this);
}

The GcmNetworkManager object will be used to schedule tasks, so one way to do this is to hold a reference as a member variable in onCreate . Alternatively, we can just get an instance of the GcmNetworkManager when we need it for scheduling.

Scheduling Tasks

Scheduling a OneOff Task

We provide the task with a window of execution, and the scheduler will determine the actual execution time. Since tasks are non-immediate, the scheduler can batch together several network calls to preserve battery life.

The scheduler will consider network availability, network activity and network load. If none of these matter, the scheduler will always wait until the end of the specified window.

Now, here’s how we would schedule a one-off task:

Task task = new OneoffTask.Builder()
              .setService(GCMService.class)
              .setExecutionWindow(0, 30)
              .setTag(LogService.TAG_TASK_ONEOFF_LOG)
              .setUpdateCurrent(false)
              .setRequiredNetwork(Task.NETWORK_STATE_CONNECTED)
              .setRequiresCharging(false)
              .build();

mGcmNetworkManager.schedule(task);

Using the builder pattern, we define all the aspects of our Task:

  • Service: The specific GcmTaskService that will control the task. This will allow us to cancel it later.
  • Execution window: The time period in which the task will execute. First param is the lower bound and the second is the upper bound (both are in seconds).
  • Tag: We’ll use the tag to identify in the onRunTask method which task is currently being run. Each tag should be unique, and the max length is 100.
  • Update Current: This determines whether this task should override any pre-existing tasks with the same tag. By default, this is false.
  • Required Network: Sets a specific network state to run on. If that network state is unavailable, then the task won’t be executed until it becomes available.
  • Requires Charging: Whether the task requires the device to be connected to power in order to execute.

All together, the task is built, scheduled on the GcmNetworkManager instance, and then eventually runs when the time is right.

Scheduling a periodic task

Here’s what a periodic task looks like:

Task task = new PeriodicTask.Builder()
                        .setService(GCMService.class)
                        .setPeriod(30)
                        .setFlex(10)
                        .setTag(LogService.TAG_TASK_PERIODIC_LOG)
                        .setPersisted(true)
                        .build();

mGcmNetworkManager.schedule(task);

It seems pretty similar, but there are a few key differences:

  • Period: Specifies that the task should recur once every interval at most, where the interval is the input param in seconds.
  • Flex: Specifies how close to the end of the period (set above) the task may execute. With a period of 30 seconds and a flex of 10, the scheduler will execute the task between the 20-30 second range.
  • Persisted: Determines whether the task should be persisted across reboots. Defaults to true for periodic tasks, and is not supported for one-off tasks. Requires “Receive Boot Completed” permission, or the setter will be ignored.

Cancelling Tasks

We saw how to schedule tasks, so now we should also take a look at how to cancel them. There’s no way to cancel a task that is currently being executed, but we can cancel any task that hasn’t yet run.

We can cancel all tasks for a given GcmTaskService:

  • gcmNetworkManager.cancelAllTasks(GCMService.class);

    And we can also cancel a specific task by providing its tag and GcmTaskService:

    gcmNetworkManager.cancelTask(
            GCMService.TAG_TASK_PERIODIC_LOG,
            GCMService.class
    );

    Well, we took a deep look at the GCM Network Manager and how to use it to conserve battery life, optimize network performance, and perform batched work using Tasks.
    I would urge you to try this out in your app for a streamlined yet robust approach on making networking calls.

Continue ReadingWorking with GCM Task Service on Android

Science Hack Day Belgaum India 2016

Announcing Science Hack Day Belgaum India – 2016

We are excited to announce our 1st Science Hack Day India. The event will take place on 22-23 October 2016 at Belgaum, a small city surrounded by some splendid nature, in Karnataka State of India.

We welcome you all to join us at SHD Belgaum. Let’s collaborate, learn, hack, build cool stuff and have lots of fun.

Registration is now open at eventbrite.

For more announcements follow us on…

facebooktwitter

What is Science Hack Day?

Science Hack Day is a two-day event where anyone excited about making weird, silly or serious things with science comes together in the same physical space to see what they can prototype within 30 consecutive hours. Designers, developers, scientists and anyone who is excited about making things with science are welcome to attend – no experience in science or hacking is necessary, just an insatiable curiosity.

The mission of Science Hack Day is to get excited and make things with science! People organically form multidisciplinary teams over the course of a weekend: particle physicists team up with designers, marketers join forces with open source rocket scientists, writers collaborate with molecular biologists, and developers partner with school kids. By collaborating on focused tasks during this short period, small groups of hackers are capable of producing remarkable results.

Venue

We have an amazing place called Sankalp Bhumi  Farm Resort for this event. It was once an abandoned quarry,  today natures glory restored. The resort resembles an enchanting oasis, with a thick set of trees, sprawling lawns, and a large lagoon surrounded by picturesque expansive rock walls as backdrop.

5

Tentative Program

Day 1:

09:00 Arrive, check-in, eat breakfast (provided)
10:00 Welcome, introductions
10:30 Hacking begins!
10:45 Lightning talks
12:00 Lunch (provided)
13:00 Hacking continues
18:00 Door closes

Day 2:

09:00 Doors open, breakfast (provided)
12:00 Lunch (provided)
13:30 Hacking stops
14:00 Hack demos begin! (Typically 2-3 minutes per demo)
16:00 Winning teams announced & given awards/medals

Science Workshops

Along with hacking we also have Science Workshops for kids. Workshops will run parallel to the SHD. We will be making amazing science toys and solar lanterns 🙂

Organisers:

FOSSASIA India Team.

Praveen Patil, Hong Phuc Dang, Rahul Khanolkar

Website: http://sciencehack.in

Continue ReadingScience Hack Day Belgaum India 2016

Features and Controls of Pocket Science Lab

Prerequisite reading:

PSLab is equipped with array of useful control and measurement tools. This tiny but powerful Pocket Science Lab enables you to perform various experiments and study a wide range of phenomena.

Some of the important applications of PSLab include a 4-channel oscilloscope, sine/triangle/square waveform generators, a frequency counter, a logic analyser and also several programmable current and voltage sources.

Add-on boards, both wired as well as wireless(NRF+MCU), enable measurement of physical parameters ranging from acceleration and angular velocity, to luminous intensity and Passive Infra-red. (Work under progress…)

As a reference for digital instruments a 12-MHz Crystal is chosen and a 3.3V voltage regulator is chosen for the analogue instruments. The device is then calibrated against professional instruments in order to squeeze out maximum performance.

Python based communication library and experiment specific PyQt4 based GUI’s make PSLab a must have tool for programmers, hobbyists, science and engineering teachers and also students.

PSLab is interfaced and powered by USB port of the computer. For connecting external signals it has several input/output terminals as shown in the figure.

pslabdesign
New panel design for PSLab

psl2

Feature list for the acquisition and control :

  • The most important feature of PSLab is a 4-channel oscilloscope which can monitor analog inputs at maximum of 2 million samples per second. Includes the usual controls such as triggering, and gain selection. Uses Python-Scipy for curve fitting.
oscilloscope
PSLab Oscilloscope

 

 

Waveform Generators

  • W1 : 5Hz – 5KHz arbitrary waveform generator. Manual amplitude control up to +/-3Volts
  • W2 : 5Hz – 5KHz arbitrary waveform generator. Amplitude of +/-3Volts. Attenuable via software
  • PWM : There are four phase correlated PWM outputs with maximum frequency 32MHz, 15nano second duty cycle, and phase difference control.

Measurement Functions

  • Frequency counter tested up to 16 MHz.
  • Capacitance Measurement. pF to uF range
  • PSLab has several 12-bit Analog inputs (function as voltmeters) with programmable gains, and maximum ranges varying from +/-5mV to +/-16V.

Voltage and Current Sources

  • 12-bit Constant Current source. Maximum current 3.3mA [subject to load resistance].
  • PSLab has three 12-bit Programmable voltage sources/ +/-3.3V,+/-5V,0-3V . (PV1, PV2, PV3)
controls
Main Control Panel

Other useful tools

  • 4MHz, 4-channel Logic analyzer with 15nS resolution.Voltage and Current Sources
  • SPI,I2C,UART outputs that can be configured and controlled entirely through Python functions. (Work in progress…)
  • On-board 2.4GHz transceiver for wireless data acquisition. (Work in progress..)
  • Graphical Interfaces for Oscilloscope, Logic Analyser, streaming data, wireless acquisition, and several experiments developed that use a common framework which drastically reduces code required to incorporate control and plotting widgets.
  • PSLab also has space for an ESP-12 module for WiFi access with access point / station mode.

Screen-shots of GUI apps.

advanced-controls
Advanced Controls with Oscilloscope
wirelesssensordataloger
Wireless Sensors ( Work in progress…)
logicanalyzer
Logic Analyzer

With all these features PSLab is taking a good shape and I see it as a potential tool that can change the way we teach and learn science. 🙂 🙂

 

Continue ReadingFeatures and Controls of Pocket Science Lab