sobota, 22 października 2016

How to create simple REST app using Spring Boot, AngularJS and MariaDB in Eclipse. Part 1



In Eclipse, File - New - Spring Starter Project. Enter Name, next, check Web. Next, Finish.

Open pom.xml and add:

<dependency>
   <groupId>org.springframework.boot</groupId>
   <artifactId>spring-boot-starter-data-jpa</artifactId>
  </dependency>
  <dependency>
   <groupId>org.mariadb.jdbc</groupId>
   <artifactId>mariadb-java-client</artifactId>
  </dependency>




Go to /src/main/resources/static/ create bower.json file:


{
  "name": "ng-spring-boot",
  "dependencies": {
    "angular": "~1.3.0",
    "angular-resource": "~1.3.0",
    "bootstrap-css-only": "~3.2.0"
  }
} 

Then, in this folder run:
$ bower install


It will create bower_components catalog with all necessary angular dependences.

Now create /src/main/resources/config/ folder with application.yml file:

# ===================================================================
# Spring Boot configuration.
#
# This configuration will be overriden by the Spring profile you use,
# for example application-dev.yml if you use the "dev" profile.
# ===================================================================

# ===================================================================
# Standard Spring Boot properties.
# Full reference is available at:
# http://docs.spring.io/spring-boot/docs/current/reference/html/common-application-properties.html
# ===================================================================

spring:
    datasource:
        url: jdbc:mariadb://localhost:3306/barfitter
        name: barfitter
        username: barfitter
        password: barfitter
    jpa:
        database-platform: org.hibernate.dialect.MySQL5InnoDBDialect
        database: MYSQL
        show-sql: true
        properties:
            hibernate.cache.use_second_level_cache: true
            hibernate.cache.use_query_cache: false
            hibernate.generate_statistics: true
    mvc:
        favicon:
            enabled: true


You must change your datasource credentials.


Now I create three entities in /src/main/java/finbarre/entities/:


package finbarre.entities;

import javax.persistence.Entity;

import java.math.BigDecimal;

import javax.persistence.*;
import javax.validation.constraints.*;
/**
 * A Vat.
 */
@Entity
@Table(name = "vat")
public class Vat  {


    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Long id;

    @NotNull
    @Column(name = "description", nullable = false)
    private String description;

    @NotNull
    @Column(name = "rate", precision=10, scale=2, nullable = false)
    private BigDecimal rate;

    @Column(name = "active")
    private Boolean active;

    public Long getId() {
        return id;
    }

    public void setId(Long id) {
        this.id = id;
    }

    public String getDescription() {
        return description;
    }

    public void setDescription(String description) {
        this.description = description;
    }

    public BigDecimal getRate() {
        return rate;
    }

    public void setRate(BigDecimal rate) {
        this.rate = rate;
    }

    public Boolean isActive() {
        return active;
    }

    public void setActive(Boolean active) {
        this.active = active;
    }



    @Override
    public String toString() {
        return "Vat{" +
            "id=" + id +
            ", description='" + description + "'" +
            ", rate='" + rate + "'" +
            ", active='" + active + "'" +
            '}';
    }
}


package finbarre.entities;

import javax.persistence.Entity;
import javax.persistence.*;
import javax.validation.constraints.*;

/**
 * A Category.
 */
@Entity
@Table(name = "category")
public class Category  {


    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Long id;

    @NotNull
    @Column(name = "name", nullable = false)
    private String name;

    @Column(name = "parent_id")
    private Integer parentId;

    public Long getId() {
        return id;
    }

    public void setId(Long id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public Integer getParentId() {
        return parentId;
    }

    public void setParentId(Integer parentId) {
        this.parentId = parentId;
    }


    @Override
    public String toString() {
        return "Category{" +
            "id=" + id +
            ", name='" + name + "'" +
            ", parentId='" + parentId + "'" +
            '}';
    }
}


package finbarre.entities;

import javax.persistence.Entity;

import java.math.BigDecimal;

import javax.persistence.*;
import javax.validation.constraints.*;



/**
 * A Product.
 */
@Entity
@Table(name = "product")
public class Product {


    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Long id;

    @NotNull
    @Column(name = "name", nullable = false)
    private String name;

    @Column(name = "purch_price_net", precision=10, scale=2)
    private BigDecimal purchPriceNet;

    @NotNull
    @Column(name = "sell_price_gross", precision=10, scale=2, nullable = false)
    private BigDecimal sellPriceGross;

    @Column(name = "active")
    private Boolean active;

    @Column(name = "self_made")
    private Boolean selfMade;

    @Column(name = "purch_price_gross", precision=10, scale=2)
    private BigDecimal purchPriceGross;

    @Column(name = "purch_vat_value", precision=10, scale=2)
    private BigDecimal purchVatValue;

    @Column(name = "sell_price_net", precision=10, scale=2)
    private BigDecimal sellPriceNet;

    @Column(name = "sell_vat_value", precision=10, scale=2)
    private BigDecimal sellVatValue;

    @ManyToOne
    private Vat productPurchPriceRate;

    @ManyToOne
    private Vat productSellPriceRate;

    @ManyToOne
    private Category category;

    public Long getId() {
        return id;
    }

    public void setId(Long id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public BigDecimal getPurchPriceNet() {
        return purchPriceNet;
    }

    public void setPurchPriceNet(BigDecimal purchPriceNet) {
        this.purchPriceNet = purchPriceNet;
    }

    public BigDecimal getSellPriceGross() {
        return sellPriceGross;
    }

    public void setSellPriceGross(BigDecimal sellPriceGross) {
        this.sellPriceGross = sellPriceGross;
    }

    public Boolean isActive() {
        return active;
    }

    public void setActive(Boolean active) {
        this.active = active;
    }

    public Boolean isSelfMade() {
        return selfMade;
    }

    public void setSelfMade(Boolean selfMade) {
        this.selfMade = selfMade;
    }

    public BigDecimal getPurchPriceGross() {
        return purchPriceGross;
    }

    public void setPurchPriceGross(BigDecimal purchPriceGross) {
        this.purchPriceGross = purchPriceGross;
    }

    public BigDecimal getPurchVatValue() {
        return purchVatValue;
    }

    public void setPurchVatValue(BigDecimal purchVatValue) {
        this.purchVatValue = purchVatValue;
    }

    public BigDecimal getSellPriceNet() {
        return sellPriceNet;
    }

    public void setSellPriceNet(BigDecimal sellPriceNet) {
        this.sellPriceNet = sellPriceNet;
    }

    public BigDecimal getSellVatValue() {
        return sellVatValue;
    }

    public void setSellVatValue(BigDecimal sellVatValue) {
        this.sellVatValue = sellVatValue;
    }

    public Vat getProductPurchPriceRate() {
        return productPurchPriceRate;
    }

    public void setProductPurchPriceRate(Vat vat) {
        this.productPurchPriceRate = vat;
    }

    public Vat getProductSellPriceRate() {
        return productSellPriceRate;
    }

    public void setProductSellPriceRate(Vat vat) {
        this.productSellPriceRate = vat;
    }

    public Category getCategory() {
        return category;
    }

    public void setCategory(Category category) {
        this.category = category;
    }



    @Override
    public String toString() {
        return "Product{" +
            "id=" + id +
            ", name='" + name + "'" +
            ", purchPriceNet='" + purchPriceNet + "'" +
            ", sellPriceGross='" + sellPriceGross + "'" +
            ", active='" + active + "'" +
            ", selfMade='" + selfMade + "'" +
            ", purchPriceGross='" + purchPriceGross + "'" +
            ", purchVatValue='" + purchVatValue + "'" +
            ", sellPriceNet='" + sellPriceNet + "'" +
            ", sellVatValue='" + sellVatValue + "'" +
            '}';
    }
}





And in /src/main/java/finbarre/repository/ we need three repositories:


package finbarre.repository;

import finbarre.entities.Vat;

import org.springframework.data.jpa.repository.*;

import java.util.List;

/**
 * Spring Data JPA repository for the Vat entity.
 */
@SuppressWarnings("unused")
public interface VatRepository extends JpaRepository<Vat,Long> {

}


package finbarre.repository;

import finbarre.entities.Category;

import org.springframework.data.jpa.repository.*;

import java.util.List;

/**
 * Spring Data JPA repository for the Category entity.
 */
@SuppressWarnings("unused")
public interface CategoryRepository extends JpaRepository<Category,Long> {

}


package finbarre.repository;

import finbarre.entities.Product;

import org.springframework.data.jpa.repository.*;

import java.util.List;

/**
 * Spring Data JPA repository for the Product entity.
 */
@SuppressWarnings("unused")
public interface ProductRepository extends JpaRepository<Product,Long> {

}


Note: we don’t need to declare new folders. We can change filenames and folders where are they placed only changing their location in headings like packages or imports.


Now we create some simple CRUD controllers for these entities:


package finbarre.controllers;

import java.util.List;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import finbarre.entities.Vat;
import finbarre.repository.VatRepository;

@RestController
@RequestMapping("/vat")
public class VatController {
  @Autowired
   private VatRepository repo;
   
   @RequestMapping(method = RequestMethod.GET)
   public List<Vat> findItems() {
     return repo.findAll();
   }
   
   @RequestMapping(method = RequestMethod.POST)
   public Vat addVat(@RequestBody Vat vat) {
    vat.setId(null);
     return repo.saveAndFlush(vat);
   }
   
   @RequestMapping(value = "/{id}", method = RequestMethod.PUT)
   public Vat updatedVat(@RequestBody Vat updatedVat, @PathVariable Long id) {
    updatedVat.setId(id);
     return repo.saveAndFlush(updatedVat);
   }
   
   @RequestMapping(value = "/{id}", method = RequestMethod.DELETE)
   public void deleteVat(@PathVariable Long id) {
     repo.delete(id);
   }
}


package finbarre.controllers;

import java.util.List;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import finbarre.entities.Category;
import finbarre.repository.CategoryRepository;

@RestController
@RequestMapping("/category")
public class CategoryController {
  @Autowired
   private CategoryRepository repo;
   
   @RequestMapping(method = RequestMethod.GET)
   public List<Category> findItems() {
     return repo.findAll();
   }
   
   @RequestMapping(method = RequestMethod.POST)
   public Category addCategory(@RequestBody Category category) {
    category.setId(null);
     return repo.saveAndFlush(category);
   }
   
   @RequestMapping(value = "/{id}", method = RequestMethod.PUT)
   public Category updatedCategory(@RequestBody Category updatedCategory, @PathVariable Long id) {
    updatedCategory.setId(id);
     return repo.saveAndFlush(updatedCategory);
   }
   
   @RequestMapping(value = "/{id}", method = RequestMethod.DELETE)
   public void deleteCategory(@PathVariable Long id) {
     repo.delete(id);
   }
}


package finbarre.controllers;

import java.util.List;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import finbarre.entities.Product;
import finbarre.repository.ProductRepository;

@RestController
@RequestMapping("/product")
public class ProductController {
  @Autowired
   private ProductRepository repo;
   
   @RequestMapping(method = RequestMethod.GET)
   public List<Product> findItems() {
     return repo.findAll();
   }
   
   @RequestMapping(method = RequestMethod.POST)
   public Product addProduct(@RequestBody Product product) {
    product.setId(null);
     return repo.saveAndFlush(product);
   }
   
   @RequestMapping(value = "/{id}", method = RequestMethod.PUT)
   public Product updatedProduct(@RequestBody Product updatedProduct, @PathVariable Long id) {
    updatedProduct.setId(id);
     return repo.saveAndFlush(updatedProduct);
   }
   
   @RequestMapping(value = "/{id}", method = RequestMethod.DELETE)
   public void deleteProduct(@PathVariable Long id) {
     repo.delete(id);
   }
}





Now you can in i.e Advanced REST Client [Chrome extension] enter http://localhost:8080/product and see products from database.







piątek, 23 września 2016

How to create new JHipster project with MySQL or MariaDB

Step 1

Create new project catalog.


Step 2

Go to this folder and run:

yo jhipster

It will create all necessary files and folders.

Step 3


In my case I use MariaDB for development and production. [For MySQL should be the same]
Create new database and user [i.e. in phpMyAdmin].

Configure database access in files:

/src/main/resources/config/application-dev.yml

and
/src/main/resources/config/application-prod.yml

Fill your access data in section:

    datasource:
        type: com.zaxxer.hikari.HikariDataSource
        url: jdbc:mariadb://localhost:3306/barfitter
        name: barfitter
        username: barfitter
        password: ************




In /pom.xml fill your access data in section:

            <plugin>
                <groupId>org.liquibase</groupId>
                <artifactId>liquibase-maven-plugin</artifactId>
                <version>${liquibase.version}</version>
                <configuration>
                    <changeLogFile>src/main/resources/config/liquibase/master.xml</changeLogFile>
                    <diffChangeLogFile>src/main/resources/config/liquibase/changelog/${maven.build.timestamp}_changelog.xml</diffChangeLogFile>
                    <driver>org.mariadb.jdbc.Driver</driver>
                    <url>jdbc:mariadb://localhost:3306/barfitter</url>
                    <defaultSchemaName></defaultSchemaName>
                    <username>barfitter</username>
                    <password>************</password>
                    <referenceUrl>hibernate:spring:com.finbarre.barfitter.domain?dialect=org.hibernate.dialect.MySQL5InnoDBDialect&amp;hibernate.ejb.naming_strategy=org.springframework.boot.orm.jpa.hibernate.SpringNamingStrategy</referenceUrl>
                    <verbose>true</verbose>
                    <logging>debug</logging>
                </configuration>



Step 4


Create new entities:
yo jhipster:entity newEntityName

Step 5


Run project:
./mvnw

Step 6


Run browsersync:
gulp

czwartek, 22 września 2016

How to add new menu and static page in JHipster

Let’s start with new menu entry

Open /src/main/webapp/app/layouts/navbar/navbar.html and find:



 <li ui-sref-active="active">
                    <a ui-sref="home" ng-click="vm.collapseNavbar()">
                        <span class="glyphicon glyphicon-home"></span>
                        <span class="hidden-sm" data-translate="global.menu.home">Home</span>
                    </a>
                </li>





After this section add new entry:


                <li ng-class="{active: vm.$state.includes('admins-jobs')}" has-authority="ROLE_ADMIN" ng-switch-when="true" uib-dropdown class="dropdown pointer">
                    <a class="dropdown-toggle" uib-dropdown-toggle href="" id="admins-jobs">
                        <span>
                            <span class="glyphicon glyphicon-th-list"></span>
                            <span class="hidden-sm" data-translate="">
                                Admin's Jobs
                            </span>
                            <b class="caret"></b>
                        </span>
                    </a>
                        <li ui-sref-active="active" >
                            <a ui-sref="static" ng-click="vm.collapseNavbar()">
                                <span class="glyphicon glyphicon-asterisk"></span>&nbsp;
                                <span data-translate="">Static page</span>
                            </a>
                        </li>
                    </ul>                
                </li>




It looks like this:





In /src/main/webapp/app/ create new catalog /static and copy there /src/main/webapp/app/home content.
Change filenames from home to static.


In static.html I left only:

<div ng-cloak>
    <div class="row">
        <div class="col-md-4">
            <span class="hipster img-responsive img-rounded"></span>
        </div>
        <div class="col-md-8">
            <h1 >Welcome, Java Hipster!</h1>
            <p class="lead" >This is your static test</p>


        </div>
    </div>
</div>




In static.state.js change:


      $stateProvider.state('home', {
to
      $stateProvider.state('static', {

---------
          url: '/',
to
          url: '/static',

---------
          parent: 'app', - change parent folder if you need

---------
                   templateUrl: 'app/home/home.html',
                   controller: 'HomeController',
to
                   templateUrl: 'app/static/static.html',
                   controller: 'StaticController',

---------

My resolve section:


           resolve: {
               translatePartialLoader: ['$translate', '$translatePartialLoader', function ($translate, $translatePartialLoader) {
                   $translatePartialLoader.addPart('global');
                   return $translate.refresh();
               }]
           }

If it’s static page, you don’t need static.controller.js.