DZone
Thanks for visiting DZone today,
Edit Profile
  • Manage Email Subscriptions
  • How to Post to DZone
  • Article Submission Guidelines
Sign Out View Profile
  • Post an Article
  • Manage My Drafts
Newsletter
Log In / Join
Refcards Trend Reports
Events Video Library
Refcards
Trend Reports

Events

View Events Video Library

Latest Articles - DZone

article thumbnail
7 Best MQTT Client Tools Worth Trying
Find a suitable client tool for MQTT testing. Listed by desktop, browser, and command line categories, these tools are available for free (most, open source).
August 12, 2022
by Li Guowei
· 10,746 Views · 1 Like
article thumbnail
What Are Ephemeral Environments and How to Deploy and Use Them Efficiently
This article will cover ephemeral environments, their benefits in the development cycle, and how Environment as a Service enables fast and reliable deployment.
August 12, 2022
by Sorin Dumitrescu
· 6,486 Views · 2 Likes
article thumbnail
Discussing Backend for Front-End
Learn more about discussing backend for front-end.
August 12, 2022
by Nicolas Fränkel
· 12,697 Views · 7 Likes
article thumbnail
Write Your Kubernetes Infrastructure as Go Code - Extend cdk8s With Custom Constructs
Build a Wordpress deployment as a cdk8s construct.
August 12, 2022
by Abhishek Gupta DZone Core CORE
· 34,493 Views · 2 Likes
article thumbnail
How to Build a Custom Application Bar for Your Windows Phone App (the Easy Way)
There is nothing quite like building the perfect customized application bar to help you feel like you have made something truly special for your users. Indeed, many users report that they appreciate the efforts that companies go through to create useful utilities within the products that they already use. A customized application bar is a wonderful tool to include because it can be used to create something that users absolutely need, and also something that they have been requesting from the companies that they work with for quite some time. The application bar makes it easier for users to find the information and resources that they are looking for without all of the struggles, and that is a critical part of making the most out of any tool. In one of my recent projects, I was forced to use icons for the application bar buttons that didn’t fit into the circled template of the standard windows phone application bar. The icons have special circles themselves, and I am not allowed to change anything on those icons (you’re right, it is for the corporate app I am working on). That's why I needed to find another solution – and I started to write my own “application bar”. As I am using Telerik's windows phone controls, I knew that the rad image button had exactly the same behavior as the buttons in the standard application bar. That point was already saved, the only thing I needed to change was the button shape of the rad image button from rectangle to ellipse – done. This is the user control I created to achieve my goal: It was a bit tricky to get all the sizes to get a similar appearance, but it does look like the original one. The radimagebutton control also has a text that we can enter, but the text was too small or too close to the button, no matter what I did. That's why there is another row in my grid with the corresponding text. You may have recognized the image with the source “overflowdots.png” above. these are located in the windows phone icon folder (in Microsoft SDKs under program files). We need this icon to generate the transition the standard application bar has. It is done with two simple storyboards: All we need now is a proper event handler – the tap event of the image inside the control is perfect for that: private void overflowdots_tap(object sender, system.windows.input.gestureeventargs e) { if (customappbarborder.actualheight == 72) { fadecustomappbarbuttontextin.begin(); } else if (customappbarborder.actualheight == 102) { fadecustomappbarbuttontextout.begin(); } } I am using a border for the animation because with a grid it was not as fluent as I wanted. That's the whole code of the control I created. let’s have a look at the implementation: The first thing is an additional row in our layout root grid, where we can add our custom app bar control (set the height to “auto”). add this code to add the app bar: //declare the control: public customappbarwp8 customappbar; //add your data to the app bar: customappbar = new customappbarwp8(); customappbar.customappbarbackground = new solidcolorbrush(colors.green); customappbar.customappbarbuttonitem1text.text = "test 1"; customappbar.customappbarbuttonitem2text.text = "test 2"; customappbar.customappbarbuttonitem3text.text = "test 3"; customappbar.customappbarbuttonitem4text.text = "test 4"; customappbar.customappbarradimagebutton1.reststateimagesource = new bitmapimage(new uri("assets/appbar/microphone.png", urikind.relativeorabsolute)); customappbar.customappbarradimagebutton2.reststateimagesource = new bitmapimage(new uri("assets/appbar/save.png", urikind.relativeorabsolute)); customappbar.customappbarradimagebutton3.reststateimagesource = new bitmapimage(new uri("assets/appbar/delete.png", urikind.relativeorabsolute)); customappbar.customappbarradimagebutton4.reststateimagesource = new bitmapimage(new uri("assets/appbar/questionmark.png", urikind.relativeorabsolute)); //registering the tap events: customappbar.customappbarradimagebutton1.tap += customappbarradimagebutton1_tap; customappbar.customappbarradimagebutton2.tap += customappbarradimagebutton2_tap; customappbar.customappbarradimagebutton3.tap += customappbarradimagebutton3_tap; customappbar.customappbarradimagebutton4.tap += customappbarradimagebutton4_tap; //adding the app bar to the dedicated grid: appbargrid.children.add(customappbar); The standard application bar does fade out the text on a button tap, so we need to add this line in every tap event. otherwise, it would remain open all the time. if (customappbar.actualheight == 102) { customappbar.fadecustomappbarbuttontextout.begin(); } To get the same result on tapping outside our custom app bar, add the same code to your main grid’s mouse left button down event. This way, you have the same behavior as in the original control. Additional note: I needed to find a quick way to achieve this, that’s why I may have not been using best practices. I also used the rad image button control to speed things up. I will refine this control when I have more time available for it, as well as add a version without Telerik controls and add the menu items. If you have any idea on how to improve this, feel free to leave a comment below. Anyways, you can download the source of the code above here: https://github.com/msiccdev/customappbar_wp8 As always, I hope this will be helpful for some of you.
August 12, 2022
by Marco Siccardi
· 11,387 Views · 1 Like
article thumbnail
Google Cloud Messaging with Android
You have probably heard a lot of talk about the wonderful things the cloud can do for you, and you are probably curious about how those services may come into play in your daily life. If this sounds like you, then you need to know that cloud services are playing an increasingly important role in our lives, and we need to look at how they can change how we message one another. Many people are looking at Android cloud messaging as the next leap forward into a future where it is possible to reach out to the people we care about and save those messages directly in the cloud. Never miss the opportunity to communicate with someone who truly matters to you, and start using cloud storage to back up your messages. It is as simple as that! You might have heard of c2dm (cloud-to-device messaging), which basically allowed third-party applications to send (push) lightweight messages to their android applications. Well, c2dm as such is now deprecated and replaced with its successor up the evolutionary ladder: GCM, or google cloud messaging. GCM is a (free) service that allows developers to push two types of messages from their application servers to any number of android devices registered with the service: collapsible, "send-to-sync" messages non-collapsible messages with a payload up to 4k in size "Collapsible" means that the most recent message overwrites the previous one. A "send-to-sync" message is used to notify a mobile application to sync its data with the server. In case the device comes online after being offline for a while, the client will only get the most recent server message. If you want to add push notifications to your android applications, the getting started guide will walk you through the setup process step by step, even supplying you with a two-part demo application (client + server) that you can just install and play around with. The setup process will provide you with the two most essential pieces of information needed to run GCM: An API Key is needed by your server to send GCM push notifications A Sender ID is needed by your clients to receive GCM messages from the server Everything is summarized in the following screen you get after using the google API console: The quickest way to write both server and client code is to install the sample demo application and tweak it to your needs. In particular, you might want to at least do any of the following: Change the demo's in-memory datastore into a real persistent one. Change the type and/or the content of push messages. Change the client's automatic device registration on start-up to a user preference so that the handset user may have the option to register/unregister for the push notifications. We'll do the last option as an example. Picking up where the demo ends, here's a quick way to set up push preferences and integrate them into your existing android application clients. in your android project-resources ( res/xml) directory, create a preference.xml file such as this one: and the corresponding activity: // package here import android.os.bundle; import android.preference.preferenceactivity; public class pushprefsactivity extends preferenceactivity { @override protected void oncreate(bundle savedinstancestate) { super.oncreate(savedinstancestate); addpreferencesfromresource(r.xml.preferences); } } the above will provide the following ui: The "enable server push" checkbox is where your android application user decides to register for your push messages. Then, it's only a matter of using that preferences class in your main activity and doing the required input processing. the following skeleton class only shows your own code add-ons to the pre-existing sample application: // package here import com.google.android.gcm.gcmregistrar; // other imports here public class mainactivity extends activity { /** these two should be static imports from a utilities class*/ public static string server_url; public static string sender_id; private boolean push_enabled; /** called when the activity is first created. */ @override public void oncreate(bundle savedinstancestate) { super.oncreate(savedinstancestate); // other code here... processpush(); } /** check push on back button * if pushprefsactivity is next activity on stack */ @override public void onresume(){ super.onresume(); processpush(); } /** * enable user to register/unregister for push notifications * 1. register user if all fields in prefs are filled and flag is set * 2. un-register if flag is un-set and user is registered * */ private void processpush(){ if( checkpushprefs() && push_enabled ){ // register for gcm using the sample app code } if(! push_enabled && gcmregistrar.isregisteredonserver(this) ){ gcmregistrar.unregister(this); } } /** check server push preferences */ private boolean checkpushprefs(){ sharedpreferences prefs = preferencemanager .getdefaultsharedpreferences(this); string name = prefs.getstring("sname", ""); string ip = prefs.getstring("sip", ""); string port = prefs.getstring("sport", ""); string senderid = prefs.getstring("sid", ""); push_enabled = prefs.getboolean("enable", false); boolean allfilled = checkallfilled(name, ip, port, senderid); if( allfilled ){ sender_id = senderid; server_url = "http://" + ip + ":" + port + "/" + name; } return allfilled; } /** checks if any number of string fields are filled */ private boolean checkallfilled(string... fields){ for (string field:fields){ if(field == null || field.length() == 0){ return false; } } return true; } } The above is pretty much self-explanatory. Now GCM push notifications have been integrated into your existing application. If you are registered, you get a system notification message at each server push, even when your application is not running. Opening up the message will automatically open your application: GCM is pretty easy to set up since most of the plumbing work is done for you. a side note: if you like to isolate the push functionality in its own sub-package, be aware that the GCM service gcmintentservice, provided by the sample application and responsible for handling GCM messages, needs to be in your main package (as indicated in the-set up documentation)—otherwise GCM won't work. When communicating with the sample server via an HTTP post, the sample client does a number of automatic retries using exponential back-off, meaning that the waiting period before a retry in case of failure is each time twice the amount of the preceding wait period, up to the maximum number of retries (5 at the time of this writing). You might want to change that if it doesn't suit you. It may not matter that much, though, since those retries are done in a separate thread (using asynctask) from the main UI thread, which therefore minimizes the effects on your mobile application's pre-existing flow of operations.
August 12, 2022
by Tony Siciliani
· 30,123 Views · 1 Like
article thumbnail
Getting started with PHP framework codeigniter
I have always worked with core PHP and was always reluctant to use any CMS (Joomla, Drupal, etc). Coincidentally I never got a chance to work on any of the frameworks in PHP. But in the current project at work, we have decided to use CodeIgniter. CodeIgniter is a lightweight open source web application framework. In short, it gives you a directory structure of a proper MVC pattern along with a lightweight built-in templating engine of its own. MVC pattern helps developers to separate business logic and the presentation layer. It requires a very minimal setup, unlike the famous PHP framework, Zend. Zend is mostly used in developing enterprise applications and is a vast framework, hence making the learning curve more difficult. On the other hand, CodeIgniter is easy to set up and easier to learn. Using Proper Frameworks It is so very important to apply the proper frameworks to any project that you are working on. When you use the best coding frameworks, you can accomplish a lot more than you might have ever dreamed was possible. Eliminating some of the noise and distractions that can take you away from truly accomplishing all that you need to is a big step in the right direction, and you will find that getting started with the right frameworks is probably what you need to do as a first step towards that goal. Otherwise, you will find yourself floundering for the right answers, and your projects just won’t turn out the way that you might have hoped that they would. Let’s Get started with CodeIgniter Of course, the first step is to download the codeigniter framework. You can download the latest stable version of Codeigniter from the following URL http://codeigniter.com/downloads/ . It will be a compressed file (zip file) that will be downloaded, just unzip it and keep it in a folder, say Codeigniter. Make sure you keep it inside the htdocs or webserver’s directory. Now it's time to configure the Codeigniter which initial settings to start working on. To do so, open the file config.php in your favorite editor. The file resides inside system/application/config directory. You will see an array called $config which stores all the configuration information, we will change only the following values and leave the rest as it is. /* |-------------------------------------------------------------------------- | Base Site URL |-------------------------------------------------------------------------- | */ //don't forget the TRAILING slash (/) $config['base_url'] = "http://localhost/codeigniter/"; Trust me, that shall be all to get you started. Some blogs/sites have shown many changes in this file, but you can play around with them when needed. You can change a lot about your application from this single file. Like you can store the session information inside a database, by simply setting up the config var $config['sess_use_database'] as TRUE, which is FALSE by default. You can also change the name of the session table from default “ci_sessions” to anything you like. Since none of the web applications runs without database, let me show you how to configure a database in this setup. I decided to pick this up in the next tutorial, but since it's pretty straightforward, let’s do it. To configure the database, open database.php which is located in the same directory as config.php i.e. system/application/config . Now change the values of the following array keys with the actual values of your MySQL server. $active_group = "default"; $active_record = TRUE; $db['default']['hostname'] = "localhost"; $db['default']['username'] = ""; //database username $db['default']['password'] = ""; //database password $db['default']['database'] = ""; //name of the database $db['default']['dbdriver'] = "mysql"; $db['default']['dbprefix'] = ""; //any table prefix, if you want to keep one $db['default']['pconnect'] = TRUE; $db['default']['db_debug'] = TRUE; $db['default']['cache_on'] = FALSE; $db['default']['cachedir'] = ""; $db['default']['char_set'] = "utf8"; $db['default']['dbcollat'] = "utf8_general_ci"; As you see the database configuration was also simple. Now it's time to develop a simple application using the CI framework. At the very beginning of this post I mentioned that CodeIgniter gives you an MVC pattern structure, so every part has a separate folder. Let us create a simple controller class to start with. To do this, let's create a class called Hello which will be written in the file called hello.php, stored inside system/application/controllers/ folder. The content of the file can be : (you can have a different class, after all, it's just a PHP class). class hello extends Controller { function __construct() { //call parent constructor parent::__construct(); } function index() { $output['header'] = "My page's header"; $output['content'] = "Here is the content of the webpage"; //load from from the system/application/views/hello.php $this->load->view('hello',$output); } } Dissect the code Now let us understand the code line by line. It's a controller class called hello which extends the default parent class called Controller. Extending the Controller class facilitates the execution of this controller. The constructor of this call simply loads the constructor of the parent class, which apparently is Controller. Next is the index(); function which has a special meaning in the CI framework. If it's present in a controller, it is executed automatically when the controller is loaded/executed. Now we output the data using the view part of the MVC pattern. if you notice the above code loads a view called hello which is a file kept inside the system/application/views/ folder. The file name should be the same as the name of the controller. And the data is provided in the form of an array, where header,content are the template variables, as shown below in the hello.php The above view renders the data which is passed on by the calling controller. Now let's try and test if everything works as we expected, phew! Open your browser and hit http://localhost/codeigniter/index.php/hello/ If everything is well, you should see a webpage, with a header and body content as specified in the controller. Wonder, how did that get rendered? CodeIgniter provides a very nice routing mechanism based on REST. The URL is so that you can call a specific controller and a method from inside the controller. But if you notice, in the above URL we have mentioned only the controller name i.e. hello, and not the function name index(). As mentioned previously, This is due to the fact that index(); function gets called automatically if it exists. Might it have been another function called render then the above URL would have been changed to http://localhost/codeigniter/index.php/hello/render/ The above URL which now call the render(); function from the hello controller. CodeIgniter was easy, no? If you think that was tough, just go through the steps again and I am sure you will understand. Since CI is the easiest framework and it lets you get started very quickly with the development. Happy Development!
August 12, 2022
by Sachin Khosla
· 11,254 Views · 1 Like
article thumbnail
Fun With Modules
Tight coupling between modules is a bad idea, and the worst form of coupling is cyclic dependencies between modules. Fortunately, there are a few techniques we can use to break the cycles. They are Callback, Escalation, and Demotion, and I’m going to walk through some examples that show each of them in action. Then, once the dependencies are broken, we’ll look at two more techniques that allow us to invert and eliminate the relationship altogether. The code for each of the samples can be found in the edcie project on my Google code repository. Each example includes a build script and a simple test case. To execute them though, you’ll need GraphViz if you want to use JarAnalyzer. To invoke the build scripts without invoking JarAnalyzer, you can simply type: ant compile Keep in mind that each variation of the system has the exact same behavior! Modules Can Teach Us Plenty There are a number of amazing lessons that we can all learn when we use modules to help mold our software products and help us create things that customers will truly want to check out. However, we should experiment carefully with the different modules that are available to us before settling on any particular one. It may be the case that we need to sample several of them before we ultimately decide that one or the other is a better use of our time. Think about this carefully, and make sure you tweak your modules as necessary to get the best possible results out of them. You may discover that there are more than a few out there that make the most sense for you in the long run. The Example The example we’re going to use to drive the remainder of our discussion is incredibly simple. We’ve got a Customer and a Bill class that we’re going to bundle into two separate modules - cust.jar and bill.jar. There’s also a test case called PaymentTest that serves as a sample client to drive the interactions between the two classes. The test case is bundled into the billtest.jar module. The initial class diagram is seen on the right. Note the bi-directional relationship between the two classes. As we progress, we’ll add more classes and abstractions to the system to help increase the modularity. Additionally, we’re going to use JarAnalyzer to illustrate the relationships between the modules and also help us assess the quality of our design. The module structure is below, as generated by JarAnalyzer. You can see how to use JarAnalyzer in the build by reviewing the build file. Again, our goal is to break the cyclic dependency between cust.jar and bill.jar, and we’re going to look at three different ways to do this before moving on to examine different ways to massage acyclic module relationships. Initial Module Structure with Cyclic Dependencies Escalation The first technique we’re going to apply is called Escalation. With Escalation, we break the cyclic dependencies by escalating the cause of the dependency to a higher-level entity. Before we do that, we need to more fully understand why a cyclic dependency exists in this example. This reason follows: A Customer has a list of Bill instances. When the payment method on Bill is invoked, the Bill needs to determine if a discount should be applied. The discount is a product of the Customer the bill belongs to, not necessarily the Bill. Therefore, the Bill class calls for a method for Customers to determine the appropriate discount amount. Think of it this way…The Customer represents a payee and we negotiate a discount with each payee. The calculation of this discounted amount is encapsulated within the Customer. To break this dependency, we want to escalate the cause of the dependency up to a higher level class - the CustomerMediator. The mediator now encapsulates the calculation of the discount and passes that to the bill class. The best way to see this change is to look at the modified PaymentTest class. Now, I’ve modified the build script and have bundled the mediator into its own module, as shown below. If you dig a bit more deeply into the class structure, you’ll wonder why I didn’t just pass the discount amount from the Customer into Bill. Don’t worry about that. This example is slightly contrived because escalation isn’t the best way to solve this type of problem. The key takeaway is that we’ve escalated the dependency up to the mediator.jar bundle, breaking the cyclic dependency. Escalating the Cause of the Cyclic Dependency Demotion A slightly better way to solve this particular type of cyclic dependency (where we have a true composite relationship between Customer and Bill) is to use demotion. With demotion, we push the cause of the dependency to a lower-level module. Exactly the opposite of escalation. We do this by introducing a DiscountCalculator class that will be passed into the Bill class. Our modified PaymentTest class will create the calculator and pass it in for us. The Customer class will serve as the factory for the DiscountCalculator, since it’s the Customer that knows the discount that must be applied. The new class structure can be seen on the right. Now we’ll modify our build script to create an additional calc.jar bundle which will contain the DiscountCalculator class. Our resulting module structure is shown below. Demoting the Cause of the Cyclic Dependency Already you can see how this is a more natural solution than escalation for this particular type of cyclic dependency problem. What’s the key difference you might ask? With escalation, notice how I would be able to deploy the cust.jar and bill.jar modules independently. While demotion is a more natural solution in this situation, it also means that to deploy bill.jar or cust.jar, I must also deploy calc.jar. The right solution is always going to be contextual and the ideal solution is likely to shift throughout the development lifecycle. Callback Using a Callback is similar to the Observer pattern. With this approach, we’ll refactor our DiscountCalculator class to an interface, and then modify the Customer class to implement this interface. This new class structure can be seen on the right. As it happens in this specific situation, using a Callback represents a combination of demotion and our initial solution. We’ll go back to passing the Customer into the Bill, but will pass it in as a DiscountCalculator type. Whereas in the Demotion example we bundled the DiscountCalculator in a separate module, we’ll now just include it in our bill.jar module. Note that putting the DiscountCalculator in the cust.jar module would introduce the cyclic dependency we’re trying to get rid of. The new module structure, which resembles our original version minus the cyclic dependency, is shown below. Using a Callback to Eliminate the Cyclic Dependency Inverting Relationships Now we’re going to play around a bit with the module relationships. While Callback seems like the most logical solution, what if we wanted to use the cust.jar module without the bill.jar module? Callback, as it’s implemented, doesn’t allow us to do this. But with a bit of trickery, I can actually invert the relationship between the cust.jar and bill.jar modules. I start by refactoring the Bill class to an interface. Then, to avoid split packages (where classes in the same package are bundled into separate modules), I move the Bill class into the same package as the Customer class. The new class diagram is shown on the right, and the inverted module structure is shown below. Inverted Module Structure Eliminating Relationships Inverting the relationships allows us to deploy the cust.jar module independent of the bill.jar module. Again, it’s all about need. But I’d like to explore another option based on another important need - the ability to test modules independently. Before inverting the relationships, I am able to test the bill.jar module independently. After inverting the relationships, I can test the cust.jar module independently. But what if I want to test (or deploy) both modules independently? To do this, I need to completely eliminate the relationship altogether. As it turns out, because I’ve got a pretty flexible class structure after I inverted the relationships (lots of abstract coupling), I can do this by simply bundling the two interfaces - Bill and DiscountCalculator - into a separate module. No other coding changes are required. I start by moving them to a new package called base. Then, I modify my build script to bundle these two interfaces into a separate base.jar module, and we successfully eliminated the relationship between the bill.jar and cust.jar modules, as shown below. Eliminating Relationships Between Modules Wrapping Up We’ve come a long way from our original version of the system. Two modules with a cyclic relationship to a module structure where the original modules don’t have any relationship to each other. This means these modules can be tested and deployed independently. If you follow this blog, you know I’ve written plenty about the tradeoffs between flexibility and complexity, use and reuse, and many other architectural and design challenges. I hope this little exercise has helped drive some of those concepts home. As a final note, to explore some of these design decisions a bit more deeply, and to examine the tradeoffs a bit more objectively, I encourage you to run the builds for each of the projects and examine the dependencies.html file in the stats directory. To do this, you’ll need to make sure JarAnalyzer is executed, which requires GraphViz. As you’ll see when comparing the initial version to the final version, we made considerable progress in improving the quality of the design.
August 12, 2022
by Kirk Knoernschild
· 15,915 Views · 1 Like
article thumbnail
Flex for J2EE Developers: The Case for Granite Data Services
For developers having worked on J2EE web applications for many years, getting into Flex will seem both very fun and familiar of the simplicity and power of ActionScript and the UI framework, and quite tedious and frustrating when it comes to developing the core application logic and the server integration. In some ways, developing Flex applications with widely used frameworks like Cairngorm and BlazeDS involves a lot of plumbing code (business delegates, service facades, conversions between JPA entities and value objects,...) and will remind you of the days of Struts and EJB2. Data is King Let’s not pretend like data isn’t and won’t continue to be a nearly invaluable tool that companies and individuals alike can use to make a lot of progress towards their end goals. If we look at things objectively, it is clearly possible that data is the most valuable resource known to man at this time. It seems like a good idea to both invest in data services and to build up one’s knowledge about what they are and why they are so important to the development of many projects at this time. If we can all learn a little more about this topic, then we stand a very good chance of being able to use data in the ways that it was designed to be used. The Granite Data Services project was started with the (ambitious) goal of providing Flex with the same kind of development model we were used to with modern J2EE frameworks. The GDS remoting functionality has been designed from the beginning to support the serialization of JPA/Hibernate detached entities and to easily connect to the most important J2EE frameworks (EJB3, Spring, Seam, Guice). In most cases, this removes the need to write and maintain service facades and value objects on the J2EE layer. In fact, that finally means that a Flex client can consume the exact same set of server services as a classic web application. Another repetitive task is to build the ActionScript model classes. GraniteDS provides the Gas3 tool that can automatically generate the ActionScript model classes from the Java data model. With the latest GraniteDS 1.1 release, the process is still improved by the Granite Eclipse builder plugin, which regenerates on the fly the necessary ActionScript classes whenever JPA entities are created or modified in the Eclipse project. You just have to write your JPA data model, and you can directly make use of the generated AS3 classes in the Flex UI layer. This is already a big step towards a more simple server integration in Flex, but GDS 1.1 brings an even simpler programming model. It targets only JBoss Seam for now but integration with Spring and EJB3 are already on the way. The Tide project aims at providing the same simplicity to build Flex/AIR applications that JBoss Seam has brought to J2EE. Tide requires almost no configuration during development and automates most of the plumbing code generally found for example in Cairngorm business delegates or service locators. Contrary to other Flex frameworks whose goal is to put all business logic on the client, Tide client/server interactions are exclusively done by method calls on exposed services, allowing to respect transaction boundaries, security, and validation rules defined by these services. Tide mainly consists of a Flex library that provides data-oriented functionality : An entity cache ensures that all managed entity instances are unique in a Tide context. This allows in particular to maintain correct data bindings between calls to remote services. A collection wrapping mechanism that enables transparent initialization of lazy collections. A Flex collection component integrated with JBoss Seam’s paged query component that can be used as a data provider for Flex UI components and supports remote sorting and filtering. Complete integration with Seam’s events, both synchronous and asynchronous, allows a Flex client to observe events raised by the server. Flex validators integrated with server-side Hibernate validator, allowing validation messages either on the fly, or after remote calls. Client support for Seam conversations. A lightweight component-based Flex framework that is deeply integrated with the other features and can advantageously replace Cairngorm or PureMVC. Let's have a look at a very simple example to see how this works. Seam component (simply extracted from the Seam booking sample): @Stateful @Name("hotelSearch") @Scope(ScopeType.SESSION) @Restrict("#{identity.loggedIn}") public class HotelSearchingAction implements HotelSearching { @PersistenceContext private EntityManager em; private String searchString; private int pageSize = 10; private int page; @DataModel private List hotels; public void find() { page = 0; queryHotels(); } ... private void queryHotels() { hotels = em.createQuery( "select h from Hotel h where lower(h.name) like #{pattern} " + "or lower(h.city) like #{pattern} or lower(h.zip) like #{pattern} " + "or lower(h.address) like #{pattern}") .setMaxResults(pageSize) .setFirstResult( page * pageSize ) .getResultList(); } ... public List getHotels() { return this.hotels; } public int getPageSize() { return pageSize; } public void setPageSize(int pageSize) { this.pageSize = pageSize; } @Factory(value="pattern", scope=ScopeType.EVENT) public String getSearchPattern() { return searchString == null ? "%" : '%' + searchString.toLowerCase().replace('*', '%') + '%'; } public String getSearchString() { return searchString; } public void setSearchString(String searchString) { this.searchString = searchString; } @Remove public void destroy() {} } MXML application: [Bindable] private var tideContext:Context = Seam.getInstance().getSeamContext(); // Components initialization in a static block { Seam.getInstance().addComponents([HotelsCtl]); } [Bindable] [In] public var hotels:ArrayCollection; private function init():void { tideContext.mainAppUI = this; // Registers the application with Tide } private function search(searchString:String):void { dispatchEvent(new TideUIEvent("search", searchString)); } Tide Flex component: import mx.collections.ArrayCollection; [Name("hotelsCtl")] [Bindable] public class HotelsCtl { [In] public var hotels:ArrayCollection; [In] public var hotelSearch:Object; [Observer("searchForHotels")] public function search(searchString:String):void { hotelSearch.searchString = text; hotelSearch.find(); } } Of course, this is an overly simple example but there is close to no code which seems unnecessary while having a clean separation of concerns between the UI, the client component, and the remote service. Building Flex applications could hardly be easier. There are a lot of choices out there today for creating rich Internet applications, each with its own set of advantages. When making the decision on which path to take, you want to get started easily but without sacrificing the ability to create a robust, scalable, and maintainable application. GraniteDS maintains this balance.
August 12, 2022
by William Draï
· 27,924 Views · 1 Like
article thumbnail
6 Myths About the Cloud That You Should Stop Believing
Learn more about the common misconceptions about using Cloud. Read more and discover how Cloud could also help your business grow.
August 12, 2022
by Pohan Lin
· 6,663 Views · 3 Likes
article thumbnail
Extending Iridium With Custom Step Definitions
Iridium makes it easy for developers to build in their own custom step definitions, removing the need to write custom code gluing Cucumber and WebDriver together.
Updated August 12, 2022
by Matthew Casperson
· 3,397 Views · 1 Like
article thumbnail
Does Datameer Support a Full Big Data Analysis Process?
Over the last few days, I had the chance to test Datameer analytics solution (das). Das is a platform for Hadoop which includes data source integration, an analytics engine, and visualization functionality. This promise of a fully integrated big data analysis process motivated me to test the product. It really includes all required functionality for data management or ETL, it provides standard tools to analyze data and there are nice ways to build visualization dashboards. For example, there are connectors for Twitter, IMAP, HDFS, or FTP available. All menus and processes are self-explaining and the complete interface is strongly Excel or spreadsheet oriented. If you are familiar with excel you can do the analyses on your big data out of the box. For a fast on-the-fly analysis performance you only work with a subset of your data and the analyses you store will then be automatically transformed into a kind of procedure. In the end – or according to a schedule you set – you “run” the analyses on your big data: Das collects the latest data for you, Das creates MapReduce jobs in the background, and updates all your spreadsheets and visualizations. To close the analysis circle you can use the connectors to write your results back to HDFS or a database such as HBase or many more technologies. Analytics the Way You Need Them There are a lot of ways that Datameer can prove useful to you, and you don’t want to discount that fact. You will discover that it is likely the case that Datameer is a great way to display a large-scale amount of data in a format that is digestible and useful to you. We can only absorb so much data as individual human beings, but we can certainly use the information that we receive to make important decisions about our business, our products, and the future experiences that our customers will have as a result. Thus, it makes sense that there are many people who want to use Datameer as a means of getting this done. If you have felt what it is like to see all of your data on a big spreadsheet and be able to visualize what it looks like coming together, then you know that you need Datameer and similar products to help you get the results that you really need. Das is really designed for big data. If you test it with small data you will be frustrated by the performance – the overhead of creating MapReduce jobs dominates in this situation. But as soon as you start with real big data analyses this overhead gets negligible and das is taking over a lot of your programming work. My Test Infrastructure The following figure provides a nice overview of the Datameer infrastructure. Das supports many data sources, it runs on all Hadoop distributions, it provides a rest API and you can add plugins as connectors for other modeling languages such as r (#rstats). I tested das version 3.1.2 running on our MapR Hadoop cluster version 3.0.2. After getting the latest package version from Datameer support the installation was straightforward and it worked out of the box. Thanks to Datameer for providing a full test license. There are several online tutorials and videos available and there are some tutorial apps. Apps are another great feature of Datameer. You can download Datameer apps which include connectors, workbooks, and visualizations for different analysis examples. And you can create your own app from your analyses and share them with your colleagues or the community. My Test Data And Analyses I tested das with the famous “airline on-time performance” data set consisting of flight arrival and departure details for all commercial flights within the USA, from October 1987 to April 2008. I downloaded all the data (including supplements) to MapR FS, created connectors for the data, and imported the data into a workbook. In the workbook I tested many classical statistical counting analyses: Grouping functionality for the airports and counting the number of flights Grouping for the airlines and calculating different statistics as mean values for the air time Using joins to add additional information like the airline name to the airline identifier Doing sorts to extract the most interesting airports depending on different measures I am not an Excel expert. so it took me some time to get used to this low-level process of doing analysis on spreadsheets. But in the end, it is a very intuitive process of creating analyses. Every new analysis will be available in a new tab in your workbook. There are several nice functionalities to support your work. For example, there is a “sheet dependencies” overview which provides information about the dependencies between sheets. Apart from the classical analyses, das provides some data mining functionality. It is called “smart analytics”. So far, it covers k-means clustering, decision trees, column dependencies, and recommendations. It works out of the box but is not yet on the level to be satisfying for real analyses. e.g. For k-means clustering, there is no support for choosing the right number of clusters (k) and you can not switch between different distance functions (default is euclidean distance). Finally, I visualized all my results in a nice “infographic”. There are many different visualization tools and parameters available. After playing around with the settings you can create a nice dashboard and share it with your colleagues. Please be aware that the complete data set is about 5 GB. Importing the data set takes about 30 minutes and running the workbook took more than 3h in my case. In the end, I split my analyses into several workbooks to improve the feasibility. Summary It was easy to get started with Datameer analytics solution (das). It is definitely a great tool to do big data analyses without any detailed Hadoop or big data knowledge. Furthermore, it covers many use cases and provides all required functionality for your daily analysis process. However, as soon as your analyses get more complex, the limitations of Datameer become apparent and you will probably look for a more powerful toolset or start implementing your big data analyses directly on Hadoop. Finally, Datameer supports many steps in the big data analysis process, it works efficiently and the usability is straightforward. But big data is more than ETL, data analysis and visualizing the results. You should never forget to think about your use case and the business value that you want to extract from your data. In the end, this is what should guide you in choosing the tools and/or implementations to use.
August 12, 2022
by Comsysto Gmbh
· 9,257 Views · 1 Like
article thumbnail
DevOps Challenges in 2019 and How to Overcome Them
Although DevOps is rising prominently as the premier cultural transformation technique for developers, it is certainly not without its challenges.
Updated August 12, 2022
by Herman Morgan
· 8,890 Views · 1 Like
article thumbnail
Creating Application using Spring Roo and Deploying on Google App Engine
Spring Roo is an rapid application development tool that helps you in rapidly building spring-based enterprise applications in the java programming language. Google app engine is a cloud computing technology that lets you run your application on Google's infrastructure. Using Spring Roo, you can develop applications that can be deployed on the Google app engine. In this tutorial, we will develop a simple application that can run on the Google app engine. Roo configures and manages your application using the Roo shell. Roo shell can be launched as a stand-alone, command-line tool, or as a view pane in the Springsource tool suite ide. Create it Fast and Effectively Most who create applications want to make them fast, and they want to make them effectively. What this means is that if they can figure out a way to create something that will both work for their users and also provide them with the speed of transaction that they need, then it is entirely possible that this will be precisely what they need to do in order to get the best results. Most are looking to Google search as a great way to get their apps out into the world, and it seems like this is as good of a place as any to start. Pushing out apps that can help the general population get the help they need with various projects means working with the most popular search engines in the world to make it happen. Thus, you should look to develop apps that work on Google in order to get the kind of results that you require. Prerequisite Before we can start using the Roo shell, we need to download and install all prerequisites. Download and install SpringSource Tool Suite 2.3.3. m2. Spring Roo 1.1.0.m2 comes bundled with STS. While installing STS, the installer asks for the location where STS should be installed. in that directory, it will create a folder with the name "roo-%release_number%" which will contain roo stuff. add %spring_roo%/roo-1.1.0.m2/bin in your path so that when you can fire roo commands from the command line. Start STS and go to the dashboard (help->dashboard) Click on the extensions tab Install the "google plugin for eclipse" and the "datanucleus plugin". Restart STS when prompted. After installing all the above we can start building the application. Conferenceregistration.roo Application Conference registration is a simple application where speakers can register themselves and create a session they want to talk about. So, we will be having two entities: speaker and presentation. Follow the instructions to create the application: Open your operating system command-line shell Create a directory named conference-registration Go to the conference-registration directory in your command-line shell Fire Roo command. You will see a roo shell as shown below. Hint command gives you the next actions you can take to manage your application. Type the hint command and press enter. Roo will tell you that first you need to create a project and for creating a project you should type 'project' and then hit tab. Hint command is very useful as you don't have to cram all the commands; it will always give you the next logical steps that you can take at that point. Roo hint command told us that we have to create the project so type the project command as shown below project --toplevelpackage com.shekhar.conference.registration --java 6 This command created a new maven project with the top-level package name as com. Shekhar.conference.registration and created directories for storing source code and other resource files. In this command, we also specified that we are using Java version 6. Once you have created the project, type in the hint command again, Roo will tell you that now you have to set up the persistence. Type the following command persistence setup --provider datanucleus --database google_app_engine --applicationid roo-gae This command set up all the things required for persistence. It creates persistence.xml and adds all the dependencies required for persistence in pom.xml. We have chosen the provider as DataNucleus and the database as google_app_engine because we are developing our application for google app engine and it uses its own data store. Applicationid is also required when we deploy our application to the Google app engine. Now our persistence setup is completed. 8. Type the hint command again, Roo will tell you that you have to create entities now. so, we need to create our entities' speaker and presentation. To create a speaker entity, we will type the following commands entity --class ~.domain.speaker --testautomatically field string --fieldname fullname --notnull field string --fieldname email --notnull --regexp ^([0-9a-za-z]([-.\w]*[0-9a-za-z])*@([0-9a-za-z][-\w]*[0-9a-za-z]\.)+[a-za-z]{2,9})$ field string --fieldname city field date --fieldname birthdate --type java.util.date --notnull field string --fieldname bio The above six lines created an entity named session with different fields. In this, we have used notnull constraint, email regex validation, date field. Spring Roo on the app engine does not support enum and references yet which means that you can't define one-one or one-to-many relationships between entities yet. These capabilities are supported on spring MVC applications but spring MVC applications can't be deployed on app engines as of now. Spring Roo Jira has these issues. They will be fixed in future releases(hope so :) ). 9. Next create the second entity of our application presentation. To create a presentation entity type the following commands on Roo shell entity --class ~.domain.presentation --testautomatically field string --fieldname title --notnull field string --fieldname description --notnull field string --fieldname speaker --notnull The above four lines created a jpa entity called presentation, located in the domain sub-package, and added three fields -- title,description and speaker. As you can see, the speaker is added as a string (just enter the full name). Spring Roo on google app engine still does not support references. 10. Now that we have created our entities, we have to create the face of our application i.e. user interface. currently, only GWT-created UI runs on the app engine. so, we will create GWT user interface. To do that type gwt setup this command will add the GWT controller as well as all the UI required stuff. This command may take a couple of minutes if you don't have those dependencies in your maven repository. 11. Next you can configure the log4j to debug level using the following command logging setup --level debug 12. Quit the Roo shell 13. You can easily run your application locally if you have maven installed on your system, simply type "mvn gwt:run" at your command line shell while you are in the same directory in which you created the project. This will launch the GWT development mode and you can test your application. Please note that applications do not run in the Google chrome browser when you run from your development environment. So, better run it in firefox. 14. To deploy your application to the Google app engine just type mvn gwt:compile gae:deploy it will ask you for app engine credentials (email id and password).
August 12, 2022
by Shekhar Gulati
· 52,849 Views · 1 Like
article thumbnail
Multi-Cloud Management: Tools, Challenges, and Best Practices
The process of tracking, securing, and optimizing multi-cloud deployment is called multi-cloud management.
August 12, 2022
by Mandar Navare
· 4,550 Views · 1 Like
article thumbnail
CouchDB vs. MariaDB: Which Is Better?
We take a comparative look at two of the most popular databases on the market today, CouchDB and MariaDB, and what each brings to the table for your team.
Updated August 12, 2022
by Subin Sabu
· 14,405 Views · 6 Likes
article thumbnail
CoffeeScript: a TDD example
CoffeeScript is a language building an abstraction over JavaScript (as the similar name suggests.) It is an abstraction over the syntax of JavaScript, not over its concepts: the language is still based on functions as objects which may bind to other objects, and prototypical inheritance. CoffeeScript favors the best practices of JavaScript by transforming abstractions you would have written anyway, or borrowed from a framework, into language concepts for maximum conciseness. It has a compilation step - as every language must compile to a lower-level one, like C or Java. Since cowboy coding is not my preferred way to work, I prepared a Test-Driven Development example by using jsTestDriver. In this article, you get two things: a CoffeeScript introduction, and the tools for unit testing it (and consequently, how to TDD with CoffeeScript). Building on Top of JavaScript There is something to be said for those who go out of their way to try to improve the infrastructure of existing programs. Many have taken a stab at it by creating tools that are a compliment to JavaScript, and it appears to have worked quite well in this case. The reason? Because JavaScript is in need of some improvements. One of the programs that people have come up with is CoffeeScript. It is literally a bit of computer code that overlays the existing JavaScript codes to make it read even more fluidly. The benefit that one gets from this is that they can start to use JavaScript in a more efficient way with fewer bumps in the road. As it stands right now, JavaScript has numerous challenging issues that we must recognize. However, that can all be amended by using JavaScript as it was intended and just working towards perfecting it. CoffeeScript is certainly not the end all be all of the programs for improving JavaScript, but it is a great step in the right direction. People should at least try out the CoffeeScript code to see if it may be useful to them in terms of improving the quality of codes that they receive from JavaScript. If so, then it will have been worth the trouble. The infrastructure The basic structure consists of two folders: src/ and lib/; remember the compilation step. We'll put .coffee files into src/ and compile them to .js equivalents in a symmetrical tree in lib/. We add also a jsTestDriver.conf file to tell the unit testing framework all the files to load, which are only the "binary" .js scripts: server: http://localhost:4224 load: - lib/*.js Compiling This is the first version of the test I've managed to write, fizzbuzztest.coffee. It is a tautology that should always pass: mytest = () -> assertEquals(1, 1) tests = { "test1is1": mytest } TestCase("tests for fizzbuzz kata", tests) You see here that functions are still first-class objects, but only anonymous functions are supported. CoffeeScript is a Python/Ruby-like language without semicolons, and there are some affinities and common backgrounds with the latter language. I still use the old syntax for calling functions for now, although parentheses can be omitted in many cases. CoffeeScript is conservative, and even accepts semicolons if you want to write them. I compiled this script with coffee -o lib/ -c src/. fizzbuzztest.js is the result: (function(){ var mytest, tests; mytest = function() { return assertEquals(1, 1); }; tests = { "test1is1": mytest }; TestCase("tests for fizzbuzz kata", tests); })(); The global namespace is not touched by default, and var keywords are automatically introduced to preserve it. When I later needed the global namespace, I wrote: this.fizzbuzz = /* ... function definition ... */ This in this case is the window object or the other global object where you execute the code. Running To run the test, we must initialize the test driver (only once): jsTestDriver java -jar JsTestDriver-1.3.2.jar --port 4224 jsTestDriver will now listen at localhost:4224. Load this URL in your browser and capture it by clicking on the link. Tests will be executed inside the browser when requested: for more details see the related article. Every time you want to run the tests, execute them from the command line: java -jar JsTestDriver-1.3.2.jar --tests all This is the complete history of my kata. Here is the final version of the code (spoiler alert!), with support for addition of other factors than 3 or 5. The code is probably uglier than average, but it compiles: tests = { "test ordinary numbers are unchanged": -> assertEquals(1, fizzbuzz(1)) assertEquals(2, fizzbuzz(2)) assertEquals(4, fizzbuzz(4)) assertEquals(142, fizzbuzz(142)) "test multiples of 3 become fizz": -> assertEquals("Fizz", fizzbuzz(3)) assertEquals("Fizz", fizzbuzz(6)) assertEquals("Fizz", fizzbuzz(9)) "test multiples of 5 become buzz": -> assertEquals("Buzz", fizzbuzz(5)) assertEquals("Buzz", fizzbuzz(10)) "test multiples of 3 and 5 become fizzbuzz": -> assertEquals("FizzBuzz", fizzbuzz(15)) assertEquals("FizzBuzz", fizzbuzz(45)) } TestCase("tests for fizzbuzz kata", tests) newRule = (word, divisor) -> (number) -> return word if number % divisor == 0 "" newFizzBuzz = (rules) -> (number) -> result = "" concatenation = (rule) -> result = result + rule(number) concatenation rule for rule in rules return result if result number fizzRule = newRule("Fizz", 3) buzzRule = newRule("Buzz", 5) this.fizzbuzz = newFizzBuzz([fizzRule, buzzRule]) Comments On The Experience CoffeeScript offers a shorter syntax, which presents a bit of a learning curve but not a steep one. I went through the whole example in 1 hour (I already knew how to use jsTestDriver, however.) Syntax shapes how you write code by making some things easier: I found myself using higher-order functions which create other ones more often, since creating a function now is just a matter of putting -> before some lines of code. Variable naming is also simpler as you just have to think of the name, not about var or polluting the scope. More time to dedicate to design, and less to language issues. Some one-liners like the instruction if the expression is handy but not essential, and are there due to Ruby's inspiration. There's, even more, to discover in CoffeeScript, such as the options for the binding of functions which helps not to lose the reference to this. However, the question is if all this convenience has more value than the time spent to learn a new language and add infrastructure to make it work - the compiler, the build hooks, and the parallel tree to ignore in your version control system.
August 12, 2022
by Giorgio Sironi
· 15,817 Views · 1 Like
article thumbnail
Clojure: Destructuring
In The Joy of Clojure (TJoC) destructuring is described as a mini-language within Clojure. It's not essential to learn this mini-language; however, as the authors of TJoC point out, destructuring facilitates concise, elegant code. Making Code More Understandable One of the scariest things for those who are just now learning how to do some coding is the fact that they have to try to figure out what a seemingly impossible set of rules and structures means for the work that they are trying to do. It is not easy at all, and many people struggle with it in big ways. Fortunately, there are some people who are going about the process of destructuring code so that it may be broken into smaller and more manageable chunks. If this is to happen, then one can easily see how they can potentially get a lot more value from the process of coding, and even how they can contribute to it for themselves in the future. We need to be as encouraging of the next generation of coders as we possibly can because there is no question that they will ultimately have an outsized impact on how the future of coding is decided. If they are best set up to understand coding and to make sense of its many intricacies, then they will be able to handle it without problems. However, we need to support and encourage them along the way, and that all begins by making coding easier to understand in general. What is destructuring? Clojure supports abstract structural binding, often called destructuring, in let binding lists, fn parameter lists, and any macro that expands into a let or fn. -- http://clojure.org/special_forms The simplest example of destructuring is assigning the values of a vector. user=> (def point [5 7]) #'user/point user=> (let [[x y] point] (println "x:" x "y:" y)) x: 5 y: 7 note: I'm using let for my examples of destructuring; however, in practice, I tend to use destructuring in function parameter lists at least as often, if not more often. I'll admit that I can't remember ever using destructuring like the first example, but it's a good starting point. A more realistic example is splitting a vector into a head and a tail. When defining a function with an arglist** you use an ampersand. The same is true in destructuring. user=> (def indexes [1 2 3]) #'user/indexes user=> (let [[x & more] indexes] (println "x:" x "more:" more)) x: 1 more: (2 3) It's also worth noting that you can bind the entire vector to a local using the :as directive. user=> (def indexes [1 2 3]) #'user/indexes user=> (let [[x & more :as full-list] indexes] (println "x:" x "more:" more "full list:" full-list)) x: 1 more: (2 3) full list: [1 2 3] Vector examples are the easiest; however, in practice I find myself using destructuring with maps far more often. Simple destructuring on a map is as easy as choosing a local name and providing the key. user=> (def point {:x 5 :y 7}) #'user/point user=> (let [{the-x :x the-y :y} point] (println "x:" the-x "y:" the-y)) x: 5 y: 7 As the example shows, the values of :x and :y are bound to locals with the names the-x and the-y. In practice we would never prepend "the-" to our local names; however, using different names provides a bit of clarity for our first example. In production code you would be much more likely to want locals with the same name as the key. This works perfectly well, as the next example shows. user=> (def point {:x 5 :y 7}) #'user/point user=> (let [{x :x y :y} point] (println "x:" x "y:" y)) x: 5 y: 7 While this works perfectly well, creating locals with the same name as the keys become tedious and annoying (especially when your keys are longer than one letter). Clojure anticipates this frustration and provides :keys directive that allows you to specify keys that you would like as locals with the same name. user=> (def point {:x 5 :y 7}) #'user/point user=> (let [{:keys [x y]} point] (println "x:" x "y:" y)) x: 5 y: 7 There are a few directives that work while destructuring maps. The above example shows the use of :keys. In practice I end up using :keys the most; however, I've also used the :as directive while working with maps. The following example illustrates the use of an :as directive to bind a local with the entire map. user=> (def point {:x 5 :y 7}) #'user/point user=> (let [{:keys [x y] :as the-point} point] (println "x:" x "y:" y "point:" the-point)) x: 5 y: 7 point: {:x 5, :y 7} We've now seen the :as directive used for both vectors and maps. In both cases, the locale is always assigned to the entire expression that is being destructured. For completeness I'll document the :or directive; however, I must admit that I've never used it in practice. The :or directive is used to assign default values when the map being destructured doesn't contain a specified key. user=> (def point {:y 7}) #'user/point user=> (let [{:keys [x y] :or {x 0 y 0} point] (println "x:" x "y:" y)) x: 0 y: 7 Lastly, it's also worth noting that you can destructure nested maps, vectors and a combination of both. The following example destructures a nested map user=> (def book {:name "SICP" :details {:pages 657 :isbn-10 "0262011530"}) #'user/book user=> (let [{name :name {pages :pages isbn-10 :isbn-10} :details} book] (println "name:" name "pages:" pages "isbn-10:" isbn-10)) name: SICP pages: 657 isbn-10: 0262011530 As you would expect, you can also use directives while destructuring nested maps. user=> (def book {:name "SICP" :details {:pages 657 :isbn-10 "0262011530"}) #'user/book user=> user=> (let [{name :name {:keys [pages isbn-10]} :details} book] (println "name:" name "pages:" pages "isbn-10:" isbn-10)) name: SICP pages: 657 isbn-10: 0262011530 Destructuring nested vectors is also very straight-forward, as the following example illustrates user=> (def numbers [[1 2][3 4]]) #'user/numbers user=> (let [[[a b][c d]] numbers] (println "a:" a "b:" b "c:" c "d:" d)) a: 1 b: 2 c: 3 d: 4 Since binding forms can be nested within one another arbitrarily, you can pull apart just about anything -- http://clojure.org/special_forms The following example destructures a map and a vector at the same time. user=> (def golfer {:name "Jim" :scores [3 5 4 5]}) #'user/golfer user=> (let [{name :name [hole1 hole2] :scores} golfer] (println "name:" name "hole1:" hole1 "hole2:" hole2)) name: Jim hole1: 3 hole2: 5 The same example can be rewritten using a function definition to show the simplicity of using destructuring in parameter lists. user=> (defn print-status [{name :name [hole1 hole2] :scores}] (println "name:" name "hole1:" hole1 "hole2:" hole2)) #'user/print-status user=> (print-status {:name "Jim" :scores [3 5 4 5]}) name: Jim hole1: 3 hole2: 5 There are other (less used) directives and deeper explanations available on http://clojure.org/special_forms and in The Joy of Clojure. I recommend both. **(defn do-something [x y & more] ... )
August 12, 2022
by Jay Fields
· 15,222 Views · 1 Like
article thumbnail
The Challenges of a JavaFX Reboot
In Jonathan Giles's post An FX Experience Retrospective, he starts by looking at the history of JavaFX and focuses on "what has happened in the world of JavaFX" in 2011. I was highly skeptical of JavaFX prior to JavaOne 2010 (see here and here for examples), but started to think more positively about it after the JavaOne 2010 and JavaOne 2011 announcements related to JavaFX. One thing that has been a little tricky about learning JavaFX since JavaOne 2011's big announcements have been knowing for certain whether a particular resource on JavaFX applies to JavaFX 1.x or JavaFX 2.x. Reading the An FX Experience Retrospective post provided a different perspective on the risks and challenges Oracle and the JavaFX team has faced in making this major overhaul. A JavaFX Reboot is Going to be a Challenge It is absolutely the case that a JavaFx Reboot will be an extreme challenge in that most people haven’t given the idea of rebooting this system much thought at all. They assume that the JavaFx system will work just as well for them today as it has in the past, but they may be making a big mistake in making such a sweeping judgment. There are many who feel that JavaFx is in need of an update/upgrade, but it is not clear how that is going to be possible. So many of the elements of JavaFX were built with a specific purpose in mind, and it is far from easy to change course on that idea at this stage of the game. Thus, it seems likely that JavaFx will largely continue to exist as it has for all of these years and not receive the upgrade that it needs at this time. However, there are at least some people who are working around the edges to see what they can do about putting the JavaFx train back on the tracks that were designed for it. Giles writes in his post, "Another vivid recollection I have from JavaOne 2010 is the various reactions that people had of this news. It varied from those in shock at losing their favorite language, to those who said it was long overdue and was the right way to proceed with JavaFX." I was in the latter group, welcoming this change and I would have liked to see it happen even sooner. The ability to use JavaFX with standard Java language and APIs was a huge benefit in my opinion and finally gave credence to the pro-JavaFX argument to Java developers that "JavaFX is Java." The JavaOne 2011 announcements of making JavaFX open source and making it part of standard Java SE were likely less controversial for Java developers (who wouldn't want these characteristics?) and are also important to me in my renewed interest in JavaFX. For developers just learning JavaFX, it can be a bit tricky to know if an online resource is for JavaFX 1.x or 2.x without delving into the article. The changes in JavaFX from 1.x to 2.x are significant enough that I generally don't want to risk confusion by reading JavaFX 1.x resources (though some have found value in reading JavaFX 1.x resources in preparation for using JavaFX 2.0). However, there are some clues that can help make it quicker and easier to identify which version of JavaFX is applicable. It is most obvious that an article is about JavaFX 2.0 when it explicitly states so. I try to do this with my blog posts on JavaFX 2.0, though I'm sure I occasionally forget to do so. When an article or blog post does not state the version of JavaFX specifically, another good clue is the date of the resource. In general, it is usually safe to assume that anything written about JavaFX before late 2010 is about JavaFX 1.x and it is similarly safe to assume that most things written about JavaFX in 2011 or later are about JavaFX 2.x. Another clue to watch for is discussion in a resource that includes JavaFX Script or FXML references. The former (JavaFX Script) was exclusive to JavaFX 1.x and the latter (FXML) is exclusive to JavaFX 2.x. Some really good documentation on JavaFX 2.x has been made available recently. The JavaFX 2.0 documentation states the following about JavaFX 2.0 versus JavaFX 1.3: JavaFX 2.0 is the latest major update release for JavaFX. Many of the new features introduced in JavaFX 2.0 are incompatible with JavaFX 1.3. If you are developing a new application in JavaFX, it is recommended that you start with JavaFX 2.0. The JavaFX 2.0 documentation contains many newly written or updated articles and posts on JavaFX 2.0. This set of documentation includes What is JavaFX?, Getting Started with JavaFX, Working with the JavaFX Scene Graph, Introduction to FXML, Getting Started with FXML, and Using JavaFX Charts. Books on JavaFX provide another perspective on the challenges associated with the major shift in JavaFX's vision. Most JavaFX books that are currently available were written for JavaFX 1.x. berry120 (who has also blogged on JavaFX 2) recently asked, Any decent books on JavaFX 2? As far as I can tell, the only JavaFX 2.x book currently available is Carl Dea's JavaFX 2.0: Introduction by Example (I hope to write a review of this short, recipe-oriented book in the near future). This book has a publication date (2011) and JavaFX 2.0 in its title, making it clear that it's on JavaFX 2.0. With books, which typically have a longer time between writing and publishing, even early 2011 publication dates might still mean a book on JavaFX 1.x. Another good clue with books is the price of used books on the Amazon Marketplace. Books on old and/or deprecated language versions tend to be very cheap. Other books on JavaFX 2.0 are likely to come. Pro JavaFXTM 2 Platform A Definitive Guide to Script, Desktop and Mobile RIA with JavaTM Technology has an advertised publication date of 12 February 2012. Carefully wading through online resources and selecting books to purchase is tricky for developers because of the major shift in JavaFX's long-term vision. Giles's post provides some insight into the even greater effort required within Oracle and the JavaFX team to make this major shift. As painful as the shift is, I believe this shift in vision coming at the cost of short-term pain provides JavaFX a fighting chance for a prosperous long-term future.
August 12, 2022
by Dustin Marx
· 10,374 Views · 4 Likes
article thumbnail
Busting PermGen Myths
In my latest post I explained the reasons that can cause the java.lang.OutOfMemoryError: PermGen space crashes. Now it is time to talk about possible solutions to the problem. Or, more precisely, about what the Internet suggests for possible solutions. Unfortunately, I can only say that I felt my inner Jamie Hyneman from MythBusters awakening when going through the different "expert opinions" on the subject. I googled for current common knowledge about ways to solve java.lang.OutOfMemoryError: PermGen space crashes and went through a couple dozen pages that seemed more appropriate in Google results. Fortunately, most of the suggestions have already been distilled into this topic of the very respected StackOverflow. As you can see, the topic is truly popular and has some quite highly voted answers. But the irony is that the whole topic contains exactly zero solutions I could recommend myself. Well, aside from “Find the cause of memory leak”, which is absolutely correct, of course, but not a very helpful way to respond to the question “How to solve memory leak”. Let us review the suggestions put forward on the SO page. Too Many Myths Exist About PermGen There are far too many myths regarding PermGen, and it has a lot of people worried as far as how they will help the public see and understand the reality of PermGen and all of the good that it can be used for in the world. The fact that so many myths continue to spread about this program is truly astounding, and there are mitigation efforts that need to be taken in order to ensure that people are not misled forever. There is serious work to do to regain trust with some people, and it is a wise idea to look at the myths that are being spread about PermGen and other services as a great starting point. We can and should do something to put a stop to this, and the time to act is right now. Use -XX:MaxPermSize=XXXM There can be two reasons that cause the java.lang.OutOfMemoryError: PermGen space error. One is that application servers and/or applications really do use so many classes that they do not fit into the default sized Permanent Generation. It is definitely possible and not that rare in fact. In this case increasing the size of the Permanent Generation can really save the day. If your only problem is how to fit too much furniture into too small a house, then buy the bigger house! But what if your over-caring mother sends you new furniture every week? You cannot possibly continue to move to the bigger houses over and over again. That is exactly the situation with memory leaks - and also with the classloader leaks, as described in my previous post that I mentioned above. Let me be clear here: no increase in Permanent Generation size will save you from the classloader leak. It can only postpone it. And make it harder to predict how many re-deployments your server will outlive. -XX:+CMSClassUnloadingEnabled -XX:+CMSPermGenSweepingEnabled The most popular answer on StackOverflow was to add these options to the server’s command line. And, they say, "maybe add -XX:+UseConcMarkSweepGC too. Just to be sure". My first problem with these JVM flags is that there is no explanation available of what they really do. Neither in the SO answer (and I don't like answers that tell you to do something without the reasoning why you should do it), nor actually in the whole Internet. Really, I was unable to find any documentation about these options, except for this page. But, in fact, that doesn't even matter. In no way any tinkering with the Garbage Collector options will help you in case of a classloader leak. Because, by definition, a memory leak is a situation where GC falls short. If there is a valid live hard reference from somewhere within your server’s classloader to an object or class of your application, then the GC will never think of it as garbage and will never reclaim it. Sure, all these JVM flags look very smart and magical. And they really may be required in some situations. But they are certainly not sufficient and don’t solve your Permanent Generation leak. Use JRockit The next proposition was to switch to the JRockit JVM. The rationale was that as JRockit has no Permanent Generation, one cannot run out of it. Surely, an interesting proposition. Unfortunately, it will not solve our problem either. The only result of this “solution” will be getting a java.lang.OutOfMemoryError: Java heap space instead of the java.lang.OutOfMemoryError: PermGen space. In the absence of separate generation for class definitions, JRockit uses the usual Java heap space for them. And as long the root cause of the leak is not fixed, those class definitions will fill up even the largest heap, given enough time. Restart the server Yet another way to pretend that the problem is solved, is to restart the application server from time to time. E.g. instead of redeploying the application, just restart the whole server. But the first time you see an application server with more than one application deployed, you will know that this is rarely possible in a production environment. And this is not really a solution. It is a way to hide your head in the sand. Use Tomcat This one is actually not that hopeless as the previous ones - recent Tomcat versions really do try to solve classloader leaks. See for yourself in their documentation. IF you can use Tomcat as your target server, and IF your leak is one of those Tomcat can successfully fight against, then maybe, just maybe, you are lucky and the problem is solved for you. Use May be a viable solution too. But again, with a couple of IFs. Firstly, you should be able to use that profiler in the affected environment. And as I have previously mentioned in my other post, profilers impose overhead of the level that might not be acceptable in the (production) environment. And secondly, you must know how to use the profiler to extract the required information and conclude the location of the leak. And my 10+ years of experience show that is very rarely the case. Conclusion So far we haven’t seen any definite solution to the java.lang.OutOfMemoryError: PermGen space error. There are a few that can be viable in some cases. But I was astounded by the fact that the majority of proposals were just plain invalid! You could waste days or weeks trying them and not even start to solve the real problem: find that rogue reference that is the root cause of the leak! Fortunately, as of the 1.1 release, Plumbr also discovers PermGen leaks. And it tells you the very reason that keeps the classloader from being freed, sparing you the time of hunting down the leak. So next time, when facing the java.lang.OutOfMemoryError: PermGen space message, download Plumbr and get rid of the problem for good.
August 12, 2022
by Nikita Salnikov-Tarnovski
· 44,439 Views · 2 Likes
  • Previous
  • ...
  • 691
  • 692
  • 693
  • 694
  • 695
  • 696
  • 697
  • 698
  • 699
  • 700
  • ...
  • Next
  • RSS
  • X
  • Facebook

ABOUT US

  • About DZone
  • Support and feedback
  • Community research

ADVERTISE

  • Advertise with DZone

CONTRIBUTE ON DZONE

  • Article Submission Guidelines
  • Become a Contributor
  • Core Program
  • Visit the Writers' Zone

LEGAL

  • Terms of Service
  • Privacy Policy

CONTACT US

  • 3343 Perimeter Hill Drive
  • Suite 215
  • Nashville, TN 37211
  • [email protected]

Let's be friends:

  • RSS
  • X
  • Facebook
×