How to lock a specified row using Apache POI? - apache-poi

I am using Apache POI to write data to an Excel file,and I want to make the first row readonly and the the other rows can be edit at any time.But I did not find an effective way to solve it.
Below is my code:
public static void createExcel(){
HSSFWorkbook workbook=new HSSFWorkbook();
HSSFSheet sheet=workbook.createSheet("Variable");
CellStyle lockStyle=workbook.createCellStyle();
lockStyle.setLocked(true);
CellStyle unlockStyle=workbook.createCellStyle();
unlockStyle.setLocked(false);
sheet.protectSheet("www.hirain.com");
for(int i=0;i<=20;i++){
Row row=sheet.createRow(i);
if(i==0){
row.setRowStyle(lockStyle);
}else{
row.setRowStyle(unlockStyle);
}
Cell c1=row.createCell(0);
Cell c2=row.createCell(1);
c1.setCellValue((char)i);
c2.setCellValue(String.valueOf((char)(65+i)));
}
try {
OutputStream out=new FileOutputStream(new File("D:\\test.xls"));
workbook.write(out);
out.flush();
out.close();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
System.out.println("=========export excel success=========");
}
It seems this java code block should work,but in fact it will not only lock the first row but also lock the empty cells in other row.
So I want to know is there an effective way to only lock the first row of the excel file using apachepoi?

its work for me
if(y==0) {
unlockedCellStyle.setLocked(true);
sheet.lockFormatCells(true);
sheet.enableLocking();
}else {
unlockedCellStyle.setLocked(false);
sheet.lockFormatCells(false);
sheet.enableLocking();
}
cell.setCellStyle(unlockedCellStyle);

Related

I have my own code to create a excel file and I want to send that as an attachment to email without saving file in local system

I am working on a case where I will be supplied with data and I will create a excel file using that data.
Right now I am creating it in my local system and later adding that as an attachment and sending through email using Java Mail Service.
But I dont want to store excel file in my local system and I want to just pass the stream object to email service and send email. So that there wont be any local storage of file still able to send attachment.
Please reply if there is any solution ?
// Created WorkBook
HSSFWorkbook workbook = new HSSFWorkbook();
FileOutputStream outputStream = new FileOutputStream(FILE_NAME)) workbook.write(outputStream);
here FILE_NAME is fully qualified system path where I will be storing file.
I want to skip this and directly send attachment
I'm using an approach like this and it is working fine:
File file = File.createTempFile("Report", "xlsx");
file.deleteOnExit();
Path path = file.toPath();
try (final FileOutputStream fileOut = new FileOutputStream(file)) {
try (final XSSFWorkbook workbook = new XSSFWorkbook()) {
//create your sheets here
workbook.write(fileOut);
return Files.readAllBytes(path);
} catch (Exception e) {
LOG.error("Error during creation of excel report", e);
throw e;
} finally {
if (path != null) {
try {
Files.delete(path);
} catch (final IOException e) {
LOG.error("Unable to delete file:" + path.toString(), e);
}
}
}
}
Write the data to a ByteArrayOutputStream, get the bytes, and use a ByteArrayDataSource to supply the data to JavaMail:
mbp.setDataHandler(new DataHandler(
new ByteArrayDataSource(bytes,
"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet")));
Workbook workbook=new XSSFWorkbook();
Sheet sheet =workbook.createSheet(" ");
Font HearderFont=workbook.createFont();
HearderFont.setBold(true);
HearderFont.setFontHeightInPoints((short)9);
HearderFont.setColor(IndexedColors.RED.getIndex());
CellStyle hearderCellStyle=workbook.createCellStyle();
hearderCellStyle.setFont(HearderFont);
//excel file maker
int rownum=1;
for(MailModelClass mailModelonbj:dataStored) {
Row row=sheet.createRow(rownum++);
row.createCell(0).setCellValue(mailModelonbj.(any));
row.createCell(1).setCellValue(mailModelonbj.(any));
row.createCell(2).setCellValue(mailModelonbj.(any));
}

Getting null pointer exception while reading excel file data [duplicate]

This question already has an answer here:
How to read multiple rows and columns in excel file with apache poi?
(1 answer)
Closed 4 years ago.
#Test
public void dataProviderMethod() throws InvocationTargetException, FileNotFoundException
{
try
{
File src=new File("D:\\TestData.xls");
FileInputStream fis=new FileInputStream(src);
HSSFWorkbook wb=new HSSFWorkbook(fis);
HSSFSheet sheet = wb.getSheetAt(0);
int rowcount=sheet.getLastRowNum()+1;
System.out.println(rowcount);
for(int i=1; i<rowcount;i++)
{
String questionType=sheet.getRow(i).getCell(0).getStringCellValue().toString();
System.out.println(questionType);
}
}
catch (IOException e)
{
e.printStackTrace();
}
}
You need to modify the code logic as below. Since, Some of the cell has blank value and hence null pointer exception is throwing. We need to handle the NULL Cell Value as below
Modified For loop Code:
//Column Index
int column=0;
for(int i=1; i<rowcount;i++){
Row r=sheet.getRow(i);
Cell c=r.getCell(column, Row.RETURN_BLANK_AS_NULL);
if(c==null){
questionType="";
}
else{
questionType=r.getCell(column).getStringCellValue();
}
System.out.println(questionType);
}

Duplicate entry '0' for key 'PRIMARY' while adding data to MYSQL([JDBCExceptionReporter:76])

getting following exception while inserting 2nd time in database from my liferay portlet.
[JDBCExceptionReporter:76] Duplicate entry '0' for key 'PRIMARY'.(i think its because my primary key value not getting auto increment)
I think have done mistake while auto incrementing the primary key in my custom portlet .but i don't know where i have to make changes for that.
if anyone can guide me about to where make the changes to solve this auto increment issue?
this is the code from auto increment been set
try {
restVar = restaurantPersistence.create(counterLocalService
.increment(restaurant.class.toString()));
} catch (SystemException e) {
e.printStackTrace();
return restVar = null;
}
try {
resourceLocalService.addResources(0,restParam.getGroupId(), restParam.getUserId(),
restaurant.class.getName(),restParam.getPrimaryKey(), false,true,true);
} catch (PortalException e) {
e.printStackTrace();
return restVar = null;
} catch (SystemException e) {
e.printStackTrace();
return restVar = null;
}
Try this one..
long primaryKeyId = CounterLocalServiceUtil.increment(ClassName.class.getName());
XYZDetails XYZDetails = XYZDetailsLocalServiceUtil.createXYZDetails(primaryKeyId);
Add other details using XYZDetails Obj
e.g
XYZDetails.setName("Name");
Then Save the Details..
XYZDetailsLocalServiceUtil.addXYZDetails(XYZDetails);
Hope this may help you !!!

adding an image component to Table cell by overidding `createCell`

I am using LWUIT and showing data with Table, say, flight information!
Instead of writing air companies with text I just like to replace them with icons.
So, I need to override protected Component createCell(Object value, final int row, final int column, boolean editable) method of Table.
This is how I've implemented:
Initializing
imgAln[i]=null;
try {
imgAln[i] = Image.createImage(strPathToImage[i]);
//e.g /uta.png,/somonair.png and so on
lAln[i] = new Label(imgAln[i]);
} catch (IOException e) { }
Creating Table object
Table table = new Table(model) {
protected Component createCell(Object value, final int row,
final int column, boolean editable) {
final Component c = super.createCell(value, row, column, editable);
if (column == 6) {
return lAln[value]; //it does not work here
}
}
};
need help to add Image to table cell!!!
Is there any example??? links are welcome!
The problem in your createCell(...) implementation is that it does not return the super.createCell(...) when the column is not 6. Also your array of labels (lAln) may not be properly created. Try my implementation below, but make sure you store the appropriate image name in the table models' column 0.
This should solve it:
TableModel model = new DefaultTableModel(
new String[]{"Uneditable", "Editable", "CheckBox", "Multiline"},
new Object[][]{
{"/animations.png", "", new Boolean(false), "Multi-line text\nright here"},
{"/buttons.png", "", new Boolean(true), "Further text that\nspans lines"},
{"/dialogs.png", "", new Boolean(true), "No span"},
{"/fonts.png", "", new Boolean(false), "Spanning\nFor\nEvery\nWord"},
});
Table table = new Table(model) {
protected Component createCell(Object value, final int row,
final int column, boolean editable) {
if (row != -1 && column == 0) {
try {
//In my case Column 0 store the resource path names
return new Label(Image.createImage((String)value));
} catch (Exception ex) {
ex.printStackTrace();
}
}
return super.createCell(value, row, column, editable);
}
};
NOTE: If you see the names instead of images in column 0 it means the image path is incorrect, fix it to see the images.
Did you manage to have a look at TableLayoutDemo.java in project LWUITDemo? If i remember it correct, this comes bundled download package LWUIT1.5.zip (or you can always google it).
Let me know if you need more specific help.

How can we read protected password excel file (.xls) with POI API

I've just learned POI and find the HSSF is very simple to read and create excel file (.xls).
However, I found some problem when want to read excel protected with password.
It took me an hour to find this solution on internet.
Please could you help me to solve this problem.
I'm very glad if you could give me a code snippet.
Thank you.
See http://poi.apache.org/encryption.html - if you're using a recent enough copy of Apache POI (eg 3.8) then encrypted .xls files (HSSF) and .xlsx files (XSSF) can be decrypted (proving you have the password!)
At the moment you can't write out encrypted excel files though, only un-encrypted ones
At the time you wrote your question, it wasn't easy to do with Apache POI. Since then, support has come on a long way
These days, if you want to open a password protected Excel file, whether .xls or .xlsx, for which you know the password, all you need to do is use WorkbookFactory.create(File,Password), eg
File input = new File("password-protected.xlsx");
String password = "nice and secure";
Workbook wb = WorkbookFactory.create(input, password);
That'll identify the type of the file, decrypt it with the given password, and open it for you. You can then read the contents as normal
Here is a complete example code that reads in a protected excel file, decrypts using a password and writes out unprotected excel file
public static void readProtectedBinFile() {
try {
InputStream inp = new FileInputStream("c:\\tmp\\protectedFile.xls");
org.apache.poi.hssf.record.crypto.Biff8EncryptionKey.setCurrentUserPassword("abracadabra");
Workbook wb;
wb = WorkbookFactory.create(inp);
// Write the output to a file
FileOutputStream fileOut;
fileOut = new FileOutputStream("c:\\tmp\\unprotectedworkbook.xlsx");
wb.write(fileOut);
fileOut.close();
} catch (InvalidFormatException e) {
e.printStackTrace();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
That is the code for Read Excel file with checking of .xls and .xlsx (with password protected or without password protected) as complete example code.
private Workbook createWorkbookByCheckExtension() throws IOException, InvalidFormatException {
Workbook workbook = null;
String filePath = "C:\\temp\\TestProtectedFile.xls";
String fileName = "TestProtectedFile.xls";
String fileExtensionName = fileName.substring(fileName.indexOf("."));
if (fileExtensionName.equals(".xls")) {
try {
FileInputStream fileInputStream = new FileInputStream(new File(filePath));
workbook = new HSSFWorkbook(fileInputStream);
} catch (EncryptedDocumentException e) {
// Checking of .xls file with password protected.
FileInputStream fileInputStream = new FileInputStream(new File(filePath));
Biff8EncryptionKey.setCurrentUserPassword("password");
workbook = new HSSFWorkbook(fileInputStream);
}
} else if (fileExtensionName.equals(".xlsx")){
// Checking of .xlsx file with password protected.
String isWorkbookLock = "";
InputStream is = null;
is = new FileInputStream(new File(filePath));
if (!is.markSupported()) {
is = new PushbackInputStream(is, 8);
}
if (POIFSFileSystem.hasPOIFSHeader(is)) {
POIFSFileSystem fs = new POIFSFileSystem(is);
EncryptionInfo info = new EncryptionInfo(fs);
Decryptor d = Decryptor.getInstance(info);
try {
d.verifyPassword("password");
is = d.getDataStream(fs);
workbook = new XSSFWorkbook(OPCPackage.open(is));
isWorkbookLock = "true";
} catch (GeneralSecurityException e) {
e.printStackTrace();
}
}
if (isWorkbookLock != "true") {
FileInputStream fileInputStream = new FileInputStream(new File(filePath));
workbook = new XSSFWorkbook(fileInputStream);
}
}
return workbook;
}
POI will not be able to read encrypted workbooks - that means that if you have protected the entire workbook (and not just a sheet), then it won't be able to read it. Otherwise, it should work.
Ravi is right. It seems you can read password protected, but not encrypted files with POI. See http://osdir.com/ml/user-poi.apache.org/2010-05/msg00118.html. The following code prints out a trace of the file
POIFSLister lister = new POIFSLister();
lister.viewFile(spreadsheetPath, true);
If you get an output mentioning encryption then you cannot open the file with POI.

Resources